Merge "Add grant for access to private information"
authorjenkins-bot <jenkins-bot@gerrit.wikimedia.org>
Mon, 15 Aug 2016 20:25:56 +0000 (20:25 +0000)
committerGerrit Code Review <gerrit@wikimedia.org>
Mon, 15 Aug 2016 20:25:56 +0000 (20:25 +0000)
286 files changed:
RELEASE-NOTES-1.28
UPGRADE
autoload.php
docs/hooks.txt
docs/kss/Makefile
includes/DefaultSettings.php
includes/FeedUtils.php
includes/MediaWiki.php
includes/OutputPage.php
includes/Preferences.php
includes/Setup.php
includes/SiteStats.php
includes/Title.php
includes/actions/InfoAction.php
includes/actions/PurgeAction.php
includes/api/ApiAuthManagerHelper.php
includes/api/ApiCreateAccount.php [deleted file]
includes/api/ApiLogin.php
includes/api/ApiQueryUsers.php
includes/api/ApiStashEdit.php
includes/api/ApiUpload.php
includes/api/i18n/bg.json
includes/api/i18n/de.json
includes/api/i18n/en.json
includes/api/i18n/eo.json
includes/api/i18n/fr.json
includes/api/i18n/gl.json
includes/api/i18n/he.json
includes/api/i18n/qqq.json
includes/api/i18n/uk.json
includes/api/i18n/zh-hans.json
includes/auth/AuthManager.php
includes/cache/BacklinkCache.php
includes/collation/IcuCollation.php
includes/content/CssContentHandler.php
includes/content/JavaScriptContentHandler.php
includes/content/JsonContentHandler.php
includes/content/TextContentHandler.php
includes/content/WikitextContentHandler.php
includes/dao/IDBAccessObject.php
includes/db/Database.php
includes/db/DatabaseMysql.php
includes/db/DatabaseMysqlBase.php
includes/db/DatabaseMysqli.php
includes/db/IDatabase.php
includes/db/loadbalancer/LBFactory.php
includes/db/loadbalancer/LBFactoryMulti.php
includes/db/loadbalancer/LBFactorySimple.php
includes/db/loadbalancer/LBFactorySingle.php
includes/db/loadbalancer/LoadBalancer.php
includes/diff/DifferenceEngine.php
includes/exception/MWException.php
includes/filebackend/lockmanager/DBLockManager.php
includes/filerepo/RepoGroup.php
includes/htmlform/HTMLForm.php
includes/htmlform/fields/HTMLFormFieldCloner.php
includes/installer/MssqlUpdater.php
includes/installer/MysqlUpdater.php
includes/installer/OracleUpdater.php
includes/installer/PostgresUpdater.php
includes/installer/SqliteUpdater.php
includes/installer/i18n/bg.json
includes/installer/i18n/dty.json [new file with mode: 0644]
includes/installer/i18n/eo.json
includes/installer/i18n/my.json
includes/installer/i18n/sv.json
includes/jobqueue/JobRunner.php
includes/libs/objectcache/BagOStuff.php
includes/libs/objectcache/MemcachedBagOStuff.php
includes/libs/objectcache/MemcachedClient.php
includes/libs/objectcache/WANObjectCache.php
includes/media/DjVuImage.php
includes/objectcache/MemcachedPeclBagOStuff.php
includes/objectcache/ObjectCache.php
includes/objectcache/RedisBagOStuff.php
includes/page/Article.php
includes/page/WikiPage.php
includes/pager/IndexPager.php
includes/parser/Parser.php
includes/resourceloader/DerivativeResourceLoaderContext.php
includes/resourceloader/ResourceLoader.php
includes/resourceloader/ResourceLoaderClientHtml.php [new file with mode: 0644]
includes/resourceloader/ResourceLoaderContext.php
includes/resourceloader/ResourceLoaderFileModule.php
includes/resourceloader/ResourceLoaderImage.php
includes/resourceloader/ResourceLoaderUserOptionsModule.php
includes/resourceloader/ResourceLoaderUserTokensModule.php
includes/session/SessionManager.php
includes/skins/SkinTemplate.php
includes/specialpage/AuthManagerSpecialPage.php
includes/specialpage/LoginSignupSpecialPage.php
includes/specialpage/SpecialPage.php
includes/specialpage/SpecialPageFactory.php
includes/specials/SpecialChangeCredentials.php
includes/specials/SpecialContributions.php
includes/specials/SpecialCreateAccount.php
includes/specials/SpecialEditWatchlist.php
includes/specials/SpecialJavaScriptTest.php
includes/specials/SpecialMostlinkedcategories.php
includes/specials/SpecialNewpages.php
includes/specials/SpecialShortpages.php
includes/specials/SpecialTags.php
includes/specials/SpecialUndelete.php
includes/specials/SpecialUpload.php
includes/specials/SpecialUploadStash.php
includes/specials/SpecialUserLogin.php
includes/specials/SpecialWatchlist.php
includes/specials/pre-authmanager/README [deleted file]
includes/specials/pre-authmanager/SpecialChangeEmail.php [deleted file]
includes/specials/pre-authmanager/SpecialChangePassword.php [deleted file]
includes/specials/pre-authmanager/SpecialCreateAccount.php [deleted file]
includes/specials/pre-authmanager/SpecialPasswordReset.php [deleted file]
includes/specials/pre-authmanager/SpecialUserlogin.php [deleted file]
includes/specials/pre-authmanager/SpecialUserlogout.php [deleted file]
includes/templates/Usercreate.php [deleted file]
includes/templates/Userlogin.php [deleted file]
includes/upload/UploadBase.php
includes/upload/UploadFromChunks.php
includes/upload/UploadFromStash.php
includes/user/User.php
includes/utils/AutoloadGenerator.php
languages/i18n/ang.json
languages/i18n/ar.json
languages/i18n/arz.json
languages/i18n/ast.json
languages/i18n/az.json
languages/i18n/azb.json
languages/i18n/ba.json
languages/i18n/bar.json
languages/i18n/bcl.json
languages/i18n/be-tarask.json
languages/i18n/be.json
languages/i18n/bg.json
languages/i18n/bho.json
languages/i18n/bn.json
languages/i18n/bs.json
languages/i18n/ca.json
languages/i18n/ckb.json
languages/i18n/cs.json
languages/i18n/cy.json
languages/i18n/da.json
languages/i18n/de.json
languages/i18n/diq.json
languages/i18n/dsb.json
languages/i18n/dty.json
languages/i18n/el.json
languages/i18n/en.json
languages/i18n/eo.json
languages/i18n/es.json
languages/i18n/et.json
languages/i18n/eu.json
languages/i18n/fa.json
languages/i18n/fi.json
languages/i18n/fr.json
languages/i18n/gd.json
languages/i18n/gl.json
languages/i18n/got.json
languages/i18n/gu.json
languages/i18n/he.json
languages/i18n/hr.json
languages/i18n/hsb.json
languages/i18n/ht.json
languages/i18n/hu.json
languages/i18n/ia.json
languages/i18n/id.json
languages/i18n/ilo.json
languages/i18n/is.json
languages/i18n/it.json
languages/i18n/ja.json
languages/i18n/jv.json
languages/i18n/kk-cyrl.json
languages/i18n/kn.json
languages/i18n/ko.json
languages/i18n/krl.json
languages/i18n/ksh.json
languages/i18n/la.json
languages/i18n/lb.json
languages/i18n/li.json
languages/i18n/lij.json
languages/i18n/lki.json
languages/i18n/lt.json
languages/i18n/lv.json
languages/i18n/mai.json
languages/i18n/map-bms.json
languages/i18n/mg.json
languages/i18n/min.json
languages/i18n/mk.json
languages/i18n/ml.json
languages/i18n/ms.json
languages/i18n/my.json
languages/i18n/nah.json
languages/i18n/nap.json
languages/i18n/nb.json
languages/i18n/nds.json
languages/i18n/ne.json
languages/i18n/nl.json
languages/i18n/nn.json
languages/i18n/pa.json
languages/i18n/pl.json
languages/i18n/pms.json
languages/i18n/pt-br.json
languages/i18n/pt.json
languages/i18n/qqq.json
languages/i18n/ro.json
languages/i18n/roa-tara.json
languages/i18n/ru.json
languages/i18n/sa.json
languages/i18n/sco.json
languages/i18n/sgs.json
languages/i18n/sh.json
languages/i18n/si.json
languages/i18n/sl.json
languages/i18n/so.json
languages/i18n/sq.json
languages/i18n/sr-ec.json
languages/i18n/sr-el.json
languages/i18n/sv.json
languages/i18n/szl.json
languages/i18n/ta.json
languages/i18n/te.json
languages/i18n/th.json
languages/i18n/tr.json
languages/i18n/tt-cyrl.json
languages/i18n/uk.json
languages/i18n/vec.json
languages/i18n/vi.json
languages/i18n/wuu.json
languages/i18n/yi.json
languages/i18n/yo.json
languages/i18n/yue.json
languages/i18n/zh-hans.json
languages/i18n/zh-hant.json
languages/messages/MessagesCs.php
languages/messages/MessagesSk.php
maintenance/archives/patch-add-rc_name_type_patrolled_timestamp_index.sql [new file with mode: 0644]
maintenance/changePassword.php
maintenance/convertExtensionToRegistration.php
maintenance/createAndPromote.php
maintenance/initEditCount.php
maintenance/mssql/tables.sql
maintenance/oracle/archives/patch-add-rc_name_type_patrolled_timestamp_index.sql [new file with mode: 0644]
maintenance/oracle/tables.sql
maintenance/postgres/tables.sql
maintenance/purgeChangedFiles.php
maintenance/storage/fixBug20757.php
maintenance/tables.sql
resources/Resources.php
resources/src/jquery/jquery.tablesorter.js
resources/src/mediawiki.action/mediawiki.action.edit.stash.js
resources/src/mediawiki.legacy/commonPrint.css
resources/src/mediawiki.legacy/oldshared.css
resources/src/mediawiki.legacy/shared.css
resources/src/mediawiki/mediawiki.js
resources/src/mediawiki/page/mediawiki.page.patrol.css [deleted file]
resources/src/mediawiki/page/mediawiki.page.patrol.print.css [deleted file]
resources/src/startup.js
tests/phpunit/ResourceLoaderTestCase.php
tests/phpunit/includes/OutputPageTest.php
tests/phpunit/includes/api/ApiLoginTest.php
tests/phpunit/includes/api/ApiTestCase.php
tests/phpunit/includes/auth/AbstractAuthenticationProviderTest.php
tests/phpunit/includes/auth/AbstractPasswordPrimaryAuthenticationProviderTest.php
tests/phpunit/includes/auth/AbstractPreAuthenticationProviderTest.php
tests/phpunit/includes/auth/AbstractPrimaryAuthenticationProviderTest.php
tests/phpunit/includes/auth/AbstractSecondaryAuthenticationProviderTest.php
tests/phpunit/includes/auth/AuthManagerTest.php
tests/phpunit/includes/auth/AuthPluginPrimaryAuthenticationProviderTest.php
tests/phpunit/includes/auth/AuthenticationRequestTest.php
tests/phpunit/includes/auth/AuthenticationRequestTestCase.php
tests/phpunit/includes/auth/AuthenticationResponseTest.php
tests/phpunit/includes/auth/CheckBlocksSecondaryAuthenticationProviderTest.php
tests/phpunit/includes/auth/ConfirmLinkSecondaryAuthenticationProviderTest.php
tests/phpunit/includes/auth/LegacyHookPreAuthenticationProviderTest.php
tests/phpunit/includes/auth/LocalPasswordPrimaryAuthenticationProviderTest.php
tests/phpunit/includes/auth/ResetPasswordSecondaryAuthenticationProviderTest.php
tests/phpunit/includes/auth/TemporaryPasswordPrimaryAuthenticationProviderTest.php
tests/phpunit/includes/auth/ThrottlePreAuthenticationProviderTest.php
tests/phpunit/includes/auth/ThrottlerTest.php
tests/phpunit/includes/db/DatabaseMysqlBaseTest.php
tests/phpunit/includes/libs/objectcache/BagOStuffTest.php
tests/phpunit/includes/resourceloader/ResourceLoaderClientHtmlTest.php [new file with mode: 0644]
tests/phpunit/includes/session/SessionManagerTest.php
tests/phpunit/includes/skins/SkinTemplateTest.php
tests/phpunit/phpunit.php
tests/qunit/suites/resources/jquery/jquery.tablesorter.test.js
tests/qunit/suites/resources/mediawiki/mediawiki.test.js

index f26f240..80166ad 100644 (file)
@@ -76,6 +76,7 @@ changes to languages because of Phabricator reports.
   BASAbali, M. Adiputra, Naval Scene, Nemo bis, NoiX180, and 아라.
 * (T135867) shn (Shan), thanks to translators Khun Sar, Piangpha,
   Saiddzone Saimawnkham, Saosukham, and Sengwan.
+* Czech (cs) and Slovak (sk) set as reciprocal fallbacks
 
 === Other changes in 1.28 ===
 * (T128697) Improved handling of large diffs.
@@ -153,7 +154,7 @@ Documentation for both end-users and site administrators is available on
 MediaWiki.org, and is covered under the GNU Free Documentation License (except
 for pages that explicitly state that their contents are in the public domain):
 
-       https://www.mediawiki.org/wiki/Documentation
+       https://www.mediawiki.org/wiki/Special:MyLanguage/Documentation
 
 == Mailing list ==
 
diff --git a/UPGRADE b/UPGRADE
index 0fff289..3ec1a22 100644 (file)
--- a/UPGRADE
+++ b/UPGRADE
@@ -1,7 +1,7 @@
 This file provides an overview of the MediaWiki upgrade process. For help with
 specific problems, check
 
-* the documentation at https://www.mediawiki.org/wiki/Special:MyLanguage/Help:Contents/
+* the documentation at https://www.mediawiki.org/wiki/Special:MyLanguage/Help:Contents
 * the mediawiki-l mailing list archive at
   http://lists.wikimedia.org/pipermail/mediawiki-l/
 * the bug tracker at https://phabricator.wikimedia.org/
index 29f986e..f6edd94 100644 (file)
@@ -28,7 +28,6 @@ $wgAutoloadLocalClasses = [
        'ApiClientLogin' => __DIR__ . '/includes/api/ApiClientLogin.php',
        'ApiComparePages' => __DIR__ . '/includes/api/ApiComparePages.php',
        'ApiContinuationManager' => __DIR__ . '/includes/api/ApiContinuationManager.php',
-       'ApiCreateAccount' => __DIR__ . '/includes/api/ApiCreateAccount.php',
        'ApiDelete' => __DIR__ . '/includes/api/ApiDelete.php',
        'ApiDisabled' => __DIR__ . '/includes/api/ApiDisabled.php',
        'ApiEditPage' => __DIR__ . '/includes/api/ApiEditPage.php',
@@ -748,8 +747,6 @@ $wgAutoloadLocalClasses = [
        'LoggedOutEditToken' => __DIR__ . '/includes/user/LoggedOutEditToken.php',
        'LoggedUpdateMaintenance' => __DIR__ . '/maintenance/Maintenance.php',
        'LoginForm' => __DIR__ . '/includes/specialpage/LoginSignupSpecialPage.php',
-       'LoginFormAuthManager' => __DIR__ . '/includes/specialpage/LoginSignupSpecialPage.php',
-       'LoginFormPreAuthManager' => __DIR__ . '/includes/specials/pre-authmanager/SpecialUserlogin.php',
        'LoginHelper' => __DIR__ . '/includes/specials/helpers/LoginHelper.php',
        'LoginSignupSpecialPage' => __DIR__ . '/includes/specialpage/LoginSignupSpecialPage.php',
        'LonelyPagesPage' => __DIR__ . '/includes/specials/SpecialLonelypages.php',
@@ -1147,6 +1144,7 @@ $wgAutoloadLocalClasses = [
        'ResetUserTokens' => __DIR__ . '/maintenance/resetUserTokens.php',
        'ResourceFileCache' => __DIR__ . '/includes/cache/ResourceFileCache.php',
        'ResourceLoader' => __DIR__ . '/includes/resourceloader/ResourceLoader.php',
+       'ResourceLoaderClientHtml' => __DIR__ . '/includes/resourceloader/ResourceLoaderClientHtml.php',
        'ResourceLoaderContext' => __DIR__ . '/includes/resourceloader/ResourceLoaderContext.php',
        'ResourceLoaderEditToolbarModule' => __DIR__ . '/includes/resourceloader/ResourceLoaderEditToolbarModule.php',
        'ResourceLoaderFileModule' => __DIR__ . '/includes/resourceloader/ResourceLoaderFileModule.php',
@@ -1281,13 +1279,10 @@ $wgAutoloadLocalClasses = [
        'SpecialChangeContentModel' => __DIR__ . '/includes/specials/SpecialChangeContentModel.php',
        'SpecialChangeCredentials' => __DIR__ . '/includes/specials/SpecialChangeCredentials.php',
        'SpecialChangeEmail' => __DIR__ . '/includes/specials/SpecialChangeEmail.php',
-       'SpecialChangeEmailPreAuthManager' => __DIR__ . '/includes/specials/pre-authmanager/SpecialChangeEmail.php',
        'SpecialChangePassword' => __DIR__ . '/includes/specials/SpecialChangePassword.php',
-       'SpecialChangePasswordPreAuthManager' => __DIR__ . '/includes/specials/pre-authmanager/SpecialChangePassword.php',
        'SpecialComparePages' => __DIR__ . '/includes/specials/SpecialComparePages.php',
        'SpecialContributions' => __DIR__ . '/includes/specials/SpecialContributions.php',
        'SpecialCreateAccount' => __DIR__ . '/includes/specials/SpecialCreateAccount.php',
-       'SpecialCreateAccountPreAuthManager' => __DIR__ . '/includes/specials/pre-authmanager/SpecialCreateAccount.php',
        'SpecialDiff' => __DIR__ . '/includes/specials/SpecialDiff.php',
        'SpecialEditTags' => __DIR__ . '/includes/specials/SpecialEditTags.php',
        'SpecialEditWatchlist' => __DIR__ . '/includes/specials/SpecialEditWatchlist.php',
@@ -1320,7 +1315,6 @@ $wgAutoloadLocalClasses = [
        'SpecialPageLanguage' => __DIR__ . '/includes/specials/SpecialPageLanguage.php',
        'SpecialPagesWithProp' => __DIR__ . '/includes/specials/SpecialPagesWithProp.php',
        'SpecialPasswordReset' => __DIR__ . '/includes/specials/SpecialPasswordReset.php',
-       'SpecialPasswordResetPreAuthManager' => __DIR__ . '/includes/specials/pre-authmanager/SpecialPasswordReset.php',
        'SpecialPermanentLink' => __DIR__ . '/includes/specials/SpecialPermanentLink.php',
        'SpecialPreferences' => __DIR__ . '/includes/specials/SpecialPreferences.php',
        'SpecialPrefixindex' => __DIR__ . '/includes/specials/SpecialPrefixindex.php',
@@ -1351,7 +1345,6 @@ $wgAutoloadLocalClasses = [
        'SpecialUploadStashTooLargeException' => __DIR__ . '/includes/specials/SpecialUploadStash.php',
        'SpecialUserLogin' => __DIR__ . '/includes/specials/SpecialUserLogin.php',
        'SpecialUserLogout' => __DIR__ . '/includes/specials/SpecialUserLogout.php',
-       'SpecialUserlogoutPreAuthManager' => __DIR__ . '/includes/specials/pre-authmanager/SpecialUserlogout.php',
        'SpecialVersion' => __DIR__ . '/includes/specials/SpecialVersion.php',
        'SpecialWatchlist' => __DIR__ . '/includes/specials/SpecialWatchlist.php',
        'SpecialWhatLinksHere' => __DIR__ . '/includes/specials/SpecialWhatlinkshere.php',
@@ -1487,8 +1480,6 @@ $wgAutoloadLocalClasses = [
        'UserOptions' => __DIR__ . '/maintenance/userOptions.inc',
        'UserPasswordPolicy' => __DIR__ . '/includes/password/UserPasswordPolicy.php',
        'UserRightsProxy' => __DIR__ . '/includes/user/UserRightsProxy.php',
-       'UsercreateTemplate' => __DIR__ . '/includes/templates/Usercreate.php',
-       'UserloginTemplate' => __DIR__ . '/includes/templates/Userlogin.php',
        'UserrightsPage' => __DIR__ . '/includes/specials/SpecialUserrights.php',
        'UsersPager' => __DIR__ . '/includes/specials/pagers/UsersPager.php',
        'UtfNormal' => __DIR__ . '/includes/compat/normal/UtfNormal.php',
index 8fa3793..5cf8ffe 100644 (file)
@@ -3373,6 +3373,18 @@ added to the descriptor
 &$radio: Boolean, if source type should be shown as radio button
 $selectedSourceType: The selected source type
 
+'UploadStashFile': Before a file is stashed (uploaded to stash).
+Note that code which has not been updated for MediaWiki 1.28 may not call this
+hook. If your extension absolutely, positively must prevent some files from
+being uploaded, use UploadVerifyFile or UploadVerifyUpload.
+$upload: (object) An instance of UploadBase, with all info about the upload
+$user: (object) An instance of User, the user uploading this file
+$props: (array) File properties, as returned by FSFile::getPropsFromPath()
+&$error: output: If the file stashing should be prevented, set this to the reason
+  in the form of array( messagename, param1, param2, ... ) or a MessageSpecifier
+  instance (you might want to use ApiMessage to provide machine-readable details
+  for the API).
+
 'UploadVerification': DEPRECATED! Use UploadVerifyFile instead.
 Additional chances to reject an uploaded file.
 $saveName: (string) destination file name
index dadfb47..392ad1a 100644 (file)
@@ -5,7 +5,7 @@ kss: kssnodecheck
 # KSS style guide
        $(eval KSS_RL_TMP := $(shell mktemp /tmp/tmp.XXXXXXXXXX))
        $(eval MODULE_STR := $(shell paste -sd "|" styleGuideModules.txt))
-# See OutputPage::makeResourceLoaderLink.
+# See ResourceLoaderClientHtml::makeLoad.
        @curl -sG "${MEDIAWIKI_LOAD_URL}?modules=${MODULE_STR}&only=styles" > $(KSS_RL_TMP)
        @node_modules/.bin/kss-node ../../resources/src/mediawiki.ui static/ --css $(KSS_RL_TMP) -t styleguide-template
        @rm $(KSS_RL_TMP)
index 87dbd97..4e08aa6 100644 (file)
@@ -1670,6 +1670,9 @@ $wgEnotifWatchlist = false;
 /**
  * Allow users to enable email notification ("enotif") when someone edits their
  * user talk page.
+ *
+ * The owner of the user talk page must also have the 'enotifusertalkpages' user
+ * preference set to true.
  */
 $wgEnotifUserTalk = false;
 
@@ -1680,9 +1683,17 @@ $wgEnotifUserTalk = false;
 $wgEnotifRevealEditorAddress = false;
 
 /**
- * Send notification mails on minor edits to watchlist pages. This is enabled
- * by default. User talk notifications are affected by this, $wgEnotifUserTalk, and
- * the nominornewtalk user right.
+ * Potentially send notification mails on minor edits to pages. This is enabled
+ * by default.  If this is false, users will never be notified on minor edits.
+ *
+ * If it is true, editors with the 'nominornewtalk' right (typically bots) will still not
+ * trigger notifications for minor edits they make (to any page, not just user talk).
+ *
+ * Finally, if the watcher/recipient has the 'enotifminoredits' user preference set to
+ * false, they will not receive notifications for minor edits.
+ *
+ * User talk notifications are also affected by $wgEnotifMinorEdits, the above settings,
+ * $wgEnotifUserTalk, and the preference described there.
  */
 $wgEnotifMinorEdits = true;
 
@@ -4447,13 +4458,6 @@ $wgPasswordPolicy = [
        ],
 ];
 
-/**
- * Disable AuthManager
- * @since 1.27
- * @deprecated since 1.27, for use during development only
- */
-$wgDisableAuthManager = false;
-
 /**
  * Configure AuthManager
  *
@@ -5058,7 +5062,7 @@ $wgGroupPermissions['user']['upload'] = true;
 $wgGroupPermissions['user']['reupload'] = true;
 $wgGroupPermissions['user']['reupload-shared'] = true;
 $wgGroupPermissions['user']['minoredit'] = true;
-$wgGroupPermissions['user']['purge'] = true; // can use ?action=purge without clicking "ok"
+$wgGroupPermissions['user']['purge'] = true;
 $wgGroupPermissions['user']['sendemail'] = true;
 $wgGroupPermissions['user']['applychangetags'] = true;
 $wgGroupPermissions['user']['changetags'] = true;
@@ -8177,13 +8181,6 @@ $wgTextModelsToParse = [
        CONTENT_MODEL_CSS, // Make categories etc work, people put them into comments.
 ];
 
-/**
- * Whether the user must enter their password to change their e-mail address
- *
- * @since 1.20
- */
-$wgRequirePasswordforEmailChange = true;
-
 /**
  * Register handlers for specific types of sites.
  *
index d7dbd22..071a3db 100644 (file)
@@ -39,6 +39,7 @@ class FeedUtils {
                global $wgRequest, $wgUser;
 
                $purge = $wgRequest->getVal( 'action' ) === 'purge';
+               // Allow users with 'purge' right to clear feed caches
                if ( $purge && $wgUser->isAllowed( 'purge' ) ) {
                        $cache = ObjectCache::getMainWANInstance();
                        $cache->delete( $timekey, 1 );
index 21857b9..7dac0ec 100644 (file)
@@ -21,6 +21,7 @@
  */
 
 use MediaWiki\Logger\LoggerFactory;
+use MediaWiki\MediaWikiServices;
 
 /**
  * The MediaWiki class is the helper class for the index.php entry point.
@@ -761,8 +762,9 @@ class MediaWiki {
         * @param string $mode Use 'fast' to always skip job running
         */
        public function restInPeace( $mode = 'fast' ) {
+               $factory = MediaWikiServices::getInstance()->getDBLoadBalancerFactory();
                // Assure deferred updates are not in the main transaction
-               wfGetLBFactory()->commitMasterChanges( __METHOD__ );
+               $factory->commitMasterChanges( __METHOD__ );
 
                // Loosen DB query expectations since the HTTP client is unblocked
                $trxProfiler = Profiler::instance()->getTransactionProfiler();
@@ -788,7 +790,6 @@ class MediaWiki {
                wfLogProfilingData();
 
                // Commit and close up!
-               $factory = wfGetLBFactory();
                $factory->commitMasterChanges( __METHOD__ );
                $factory->shutdown( LBFactory::SHUTDOWN_NO_CHRONPROT );
 
index b88db92..cc377bc 100644 (file)
@@ -154,6 +154,15 @@ class OutputPage extends ContextSource {
        /** @var ResourceLoader */
        protected $mResourceLoader;
 
+       /** @var ResourceLoaderClientHtml */
+       private $rlClient;
+
+       /** @var ResourceLoaderContext */
+       private $rlClientContext;
+
+       /** @var string */
+       private $rlUserModuleState;
+
        /** @var array */
        protected $mJsConfigVars = [];
 
@@ -501,7 +510,7 @@ class OutputPage extends ContextSource {
         * Add a self-contained script tag with the given contents
         * Internal use only. Use OutputPage::addModules() if possible.
         *
-        * @param string $script JavaScript text, no "<script>" tags
+        * @param string $script JavaScript text, no script tags
         */
        public function addInlineScript( $script ) {
                $this->mScripts .= Html::inlineScript( $script );
@@ -541,10 +550,12 @@ class OutputPage extends ContextSource {
         * @param string $param
         * @return array Array of module names
         */
-       public function getModules( $filter = false, $position = null, $param = 'mModules' ) {
+       public function getModules( $filter = false, $position = null, $param = 'mModules',
+               $type = ResourceLoaderModule::TYPE_COMBINED
+       ) {
                $modules = array_values( array_unique( $this->$param ) );
                return $filter
-                       ? $this->filterModules( $modules, $position )
+                       ? $this->filterModules( $modules, $position, $type )
                        : $modules;
        }
 
@@ -564,11 +575,12 @@ class OutputPage extends ContextSource {
         *
         * @param bool $filter
         * @param string|null $position
-        *
         * @return array Array of module names
         */
        public function getModuleScripts( $filter = false, $position = null ) {
-               return $this->getModules( $filter, $position, 'mModuleScripts' );
+               return $this->getModules( $filter, $position, 'mModuleScripts',
+                       ResourceLoaderModule::TYPE_SCRIPTS
+               );
        }
 
        /**
@@ -587,11 +599,12 @@ class OutputPage extends ContextSource {
         *
         * @param bool $filter
         * @param string|null $position
-        *
         * @return array Array of module names
         */
        public function getModuleStyles( $filter = false, $position = null ) {
-               return $this->getModules( $filter, $position, 'mModuleStyles' );
+               return $this->getModules( $filter, $position, 'mModuleStyles',
+                       ResourceLoaderModule::TYPE_STYLES
+               );
        }
 
        /**
@@ -2265,7 +2278,7 @@ class OutputPage extends ContextSource {
                        // add skin specific modules
                        $modules = $sk->getDefaultModules();
 
-                       // Enforce various default modules for all skins
+                       // Enforce various default modules for all pages and all skins
                        $coreModules = [
                                // Keep this list as small as possible
                                'site',
@@ -2287,6 +2300,7 @@ class OutputPage extends ContextSource {
                        // Hook that allows last minute changes to the output page, e.g.
                        // adding of CSS or Javascript by extensions.
                        Hooks::run( 'BeforePageDisplay', [ &$this, &$sk ] );
+                       $this->getSkin()->setupSkinUserCss( $this );
 
                        try {
                                $sk->outputPage();
@@ -2611,6 +2625,70 @@ class OutputPage extends ContextSource {
                $this->addReturnTo( $titleObj, wfCgiToArray( $returntoquery ) );
        }
 
+       private function getRlClientContext() {
+               if ( !$this->rlClientContext ) {
+                       $query = ResourceLoader::makeLoaderQuery(
+                               [], // modules; not relevant
+                               $this->getLanguage()->getCode(),
+                               $this->getSkin()->getSkinName(),
+                               $this->getUser()->isLoggedIn() ? $this->getUser()->getName() : null,
+                               null, // version; not relevant
+                               ResourceLoader::inDebugMode(),
+                               null, // only; not relevant
+                               $this->isPrintable(),
+                               $this->getRequest()->getBool( 'handheld' )
+                       );
+                       $this->rlClientContext = new ResourceLoaderContext(
+                               $this->getResourceLoader(),
+                               new FauxRequest( $query )
+                       );
+               }
+               return $this->rlClientContext;
+       }
+
+       /**
+        * Call this to freeze the module queue and JS config and create a formatter.
+        *
+        * Depending on the Skin, this may get lazy-initialised in either headElement() or
+        * getBottomScripts(). See SkinTemplate::prepareQuickTemplate(). Calling this too early may
+        * cause unexpected side-effects since disallowUserJs() may be called at any time to change
+        * the module filters retroactively. Skins and extension hooks may also add modules until very
+        * late in the request lifecycle.
+        *
+        * @return ResourceLoaderClientHtml
+        */
+       public function getRlClient() {
+               if ( !$this->rlClient ) {
+                       $context = $this->getRlClientContext();
+                       $userModule = $this->getResourceLoader()->getModule( 'user' );
+                       // Manually handled by getBottomScripts()
+                       $userState = $userModule->isKnownEmpty( $context ) && !$this->isUserModulePreview()
+                               ? 'ready'
+                               : 'loading';
+                       $this->rlUserModuleState = $userState;
+
+                       $this->addModules( [
+                               'user.options',
+                               'user.tokens',
+                       ] );
+                       $rlClient = new ResourceLoaderClientHtml( $context );
+                       $rlClient->setConfig( $this->getJSVars() );
+                       $rlClient->setModules( $this->getModules( /*filter*/ true ) );
+                       $rlClient->setModuleStyles( $this->getModuleStyles( /*filter*/ true ) );
+                       $rlClient->setModuleScripts( $this->getModuleScripts( /*filter*/ true ) );
+                       $rlClient->setExemptStates( [
+                               'user' => $userState,
+                               // Manually handled by buildExemptModules() and getBottomScripts()
+                               'site.styles' => 'ready',
+                               'noscript' => 'ready',
+                               'user.cssprefs' => 'ready',
+                               'user.styles' => 'ready',
+                       ] );
+                       $this->rlClient = $rlClient;
+               }
+               return $this->rlClient;
+       }
+
        /**
         * @param Skin $sk The given Skin
         * @param bool $includeStyle Unused
@@ -2623,17 +2701,16 @@ class OutputPage extends ContextSource {
                $sitedir = $wgContLang->getDir();
 
                $pieces = [];
-               $pieces[] = Html::htmlHeader( $sk->getHtmlElementAttributes() );
+               $pieces[] = Html::htmlHeader( Sanitizer::mergeAttributes(
+                       $this->getRlClient()->getDocumentAttributes(),
+                       $sk->getHtmlElementAttributes()
+               ) );
+               $pieces[] = Html::openElement( 'head' );
 
                if ( $this->getHTMLTitle() == '' ) {
                        $this->setHTMLTitle( $this->msg( 'pagetitle', $this->getPageTitle() )->inContentLanguage() );
                }
 
-               $openHead = Html::openElement( 'head' );
-               if ( $openHead ) {
-                       $pieces[] = $openHead;
-               }
-
                if ( !Html::isXmlMimeType( $this->getConfig()->get( 'MimeType' ) ) ) {
                        // Add <meta charset="UTF-8">
                        // This should be before <title> since it defines the charset used by
@@ -2647,22 +2724,11 @@ class OutputPage extends ContextSource {
                }
 
                $pieces[] = Html::element( 'title', null, $this->getHTMLTitle() );
-               $pieces[] = $this->getInlineHeadScripts();
-               $pieces[] = $this->buildCssLinks();
-               $pieces[] = $this->getExternalHeadScripts();
-
-               foreach ( $this->getHeadLinksArray() as $item ) {
-                       $pieces[] = $item;
-               }
-
-               foreach ( $this->mHeadItems as $item ) {
-                       $pieces[] = $item;
-               }
-
-               $closeHead = Html::closeElement( 'head' );
-               if ( $closeHead ) {
-                       $pieces[] = $closeHead;
-               }
+               $pieces[] = $this->getRlClient()->getHeadHtml();
+               $pieces[] = $this->buildExemptModules();
+               $pieces = array_merge( $pieces, array_values( $this->getHeadLinksArray() ) );
+               $pieces = array_merge( $pieces, array_values( $this->mHeadItems ) );
+               $pieces[] = Html::closeElement( 'head' );
 
                $bodyClasses = [];
                $bodyClasses[] = 'mediawiki';
@@ -2697,7 +2763,7 @@ class OutputPage extends ContextSource {
 
                $pieces[] = Html::openElement( 'body', $bodyAttrs );
 
-               return WrappedStringList::join( "\n", $pieces );
+               return self::combineWrappedStrings( $pieces );
        }
 
        /**
@@ -2716,388 +2782,98 @@ class OutputPage extends ContextSource {
        }
 
        /**
-        * Construct neccecary html and loader preset states to load modules on a page.
-        *
-        * Use getHtmlFromLoaderLinks() to convert this array to HTML.
+        * Explicily load or embed modules on a page.
         *
         * @param array|string $modules One or more module names
         * @param string $only ResourceLoaderModule TYPE_ class constant
         * @param array $extraQuery [optional] Array with extra query parameters for the request
-        * @return array A list of HTML strings and array of client loader preset states
+        * @return string|WrappedStringList HTML
         */
        public function makeResourceLoaderLink( $modules, $only, array $extraQuery = [] ) {
-               $modules = (array)$modules;
-
-               $links = [
-                       // List of html strings
-                       'html' => [],
-                       // Associative array of module names and their states
-                       'states' => [],
-               ];
-
-               if ( !count( $modules ) ) {
-                       return $links;
-               }
-
-               if ( count( $modules ) > 1 ) {
-                       // Remove duplicate module requests
-                       $modules = array_unique( $modules );
-                       // Sort module names so requests are more uniform
-                       sort( $modules );
-
-                       if ( ResourceLoader::inDebugMode() ) {
-                               // Recursively call us for every item
-                               foreach ( $modules as $name ) {
-                                       $link = $this->makeResourceLoaderLink( $name, $only, $extraQuery );
-                                       $links['html'] = array_merge( $links['html'], $link['html'] );
-                                       $links['states'] += $link['states'];
-                               }
-                               return $links;
-                       }
-               }
-
-               if ( !is_null( $this->mTarget ) ) {
-                       $extraQuery['target'] = $this->mTarget;
-               }
-
-               // Create keyed-by-source and then keyed-by-group list of module objects from modules list
-               $sortedModules = [];
-               $resourceLoader = $this->getResourceLoader();
-               foreach ( $modules as $name ) {
-                       $module = $resourceLoader->getModule( $name );
-                       # Check that we're allowed to include this module on this page
-                       if ( !$module
-                               || ( $module->getOrigin() > $this->getAllowedModules( ResourceLoaderModule::TYPE_SCRIPTS )
-                                       && $only == ResourceLoaderModule::TYPE_SCRIPTS )
-                               || ( $module->getOrigin() > $this->getAllowedModules( ResourceLoaderModule::TYPE_STYLES )
-                                       && $only == ResourceLoaderModule::TYPE_STYLES )
-                               || ( $module->getOrigin() > $this->getAllowedModules( ResourceLoaderModule::TYPE_COMBINED )
-                                       && $only == ResourceLoaderModule::TYPE_COMBINED )
-                               || ( $this->mTarget && !in_array( $this->mTarget, $module->getTargets() ) )
-                       ) {
-                               continue;
-                       }
-
-                       if ( $only === ResourceLoaderModule::TYPE_STYLES ) {
-                               if ( $module->getType() !== ResourceLoaderModule::LOAD_STYLES ) {
-                                       $logger = $resourceLoader->getLogger();
-                                       $logger->debug( 'Unexpected general module "{module}" in styles queue.', [
-                                               'module' => $name,
-                                       ] );
-                               } else {
-                                       $links['states'][$name] = 'ready';
-                               }
-                       }
-
-                       $sortedModules[$module->getSource()][$module->getGroup()][$name] = $module;
-               }
-
-               foreach ( $sortedModules as $source => $groups ) {
-                       foreach ( $groups as $group => $grpModules ) {
-                               // Special handling for user-specific groups
-                               $user = null;
-                               if ( ( $group === 'user' || $group === 'private' ) && $this->getUser()->isLoggedIn() ) {
-                                       $user = $this->getUser()->getName();
-                               }
-
-                               // Create a fake request based on the one we are about to make so modules return
-                               // correct timestamp and emptiness data
-                               $query = ResourceLoader::makeLoaderQuery(
-                                       [], // modules; not determined yet
-                                       $this->getLanguage()->getCode(),
-                                       $this->getSkin()->getSkinName(),
-                                       $user,
-                                       null, // version; not determined yet
-                                       ResourceLoader::inDebugMode(),
-                                       $only === ResourceLoaderModule::TYPE_COMBINED ? null : $only,
-                                       $this->isPrintable(),
-                                       $this->getRequest()->getBool( 'handheld' ),
-                                       $extraQuery
-                               );
-                               $context = new ResourceLoaderContext( $resourceLoader, new FauxRequest( $query ) );
-
-                               // Extract modules that know they're empty and see if we have one or more
-                               // raw modules
-                               $isRaw = false;
-                               foreach ( $grpModules as $key => $module ) {
-                                       // Inline empty modules: since they're empty, just mark them as 'ready' (bug 46857)
-                                       // If we're only getting the styles, we don't need to do anything for empty modules.
-                                       if ( $module->isKnownEmpty( $context ) ) {
-                                               unset( $grpModules[$key] );
-                                               if ( $only !== ResourceLoaderModule::TYPE_STYLES ) {
-                                                       $links['states'][$key] = 'ready';
-                                               }
-                                       }
-
-                                       $isRaw |= $module->isRaw();
-                               }
-
-                               // If there are no non-empty modules, skip this group
-                               if ( count( $grpModules ) === 0 ) {
-                                       continue;
-                               }
-
-                               // Inline private modules. These can't be loaded through load.php for security
-                               // reasons, see bug 34907. Note that these modules should be loaded from
-                               // getExternalHeadScripts() before the first loader call. Otherwise other modules can't
-                               // properly use them as dependencies (bug 30914)
-                               if ( $group === 'private' ) {
-                                       if ( $only == ResourceLoaderModule::TYPE_STYLES ) {
-                                               $links['html'][] = Html::inlineStyle(
-                                                       $resourceLoader->makeModuleResponse( $context, $grpModules )
-                                               );
-                                       } else {
-                                               $links['html'][] = ResourceLoader::makeInlineScript(
-                                                       $resourceLoader->makeModuleResponse( $context, $grpModules )
-                                               );
-                                       }
-                                       continue;
-                               }
-
-                               // Special handling for the user group; because users might change their stuff
-                               // on-wiki like user pages, or user preferences; we need to find the highest
-                               // timestamp of these user-changeable modules so we can ensure cache misses on change
-                               // This should NOT be done for the site group (bug 27564) because anons get that too
-                               // and we shouldn't be putting timestamps in CDN-cached HTML
-                               $version = null;
-                               if ( $group === 'user' ) {
-                                       $query['version'] = $resourceLoader->getCombinedVersion( $context, array_keys( $grpModules ) );
-                               }
-
-                               $query['modules'] = ResourceLoader::makePackedModulesString( array_keys( $grpModules ) );
-                               $moduleContext = new ResourceLoaderContext( $resourceLoader, new FauxRequest( $query ) );
-                               $url = $resourceLoader->createLoaderURL( $source, $moduleContext, $extraQuery );
-
-                               // Automatically select style/script elements
-                               if ( $only === ResourceLoaderModule::TYPE_STYLES ) {
-                                       $link = Html::linkedStyle( $url );
-                               } else {
-                                       if ( $context->getRaw() || $isRaw ) {
-                                               // Startup module can't load itself, needs to use <script> instead of mw.loader.load
-                                               $link = Html::element( 'script', [
-                                                       // In SpecialJavaScriptTest, QUnit must load synchronous
-                                                       'async' => !isset( $extraQuery['sync'] ),
-                                                       'src' => $url
-                                               ] );
-                                       } else {
-                                               $link = ResourceLoader::makeInlineScript(
-                                                       Xml::encodeJsCall( 'mw.loader.load', [ $url ] )
-                                               );
-                                       }
-
-                                       // For modules requested directly in the html via <script> or mw.loader.load
-                                       // tell mw.loader they are being loading to prevent duplicate requests.
-                                       foreach ( $grpModules as $key => $module ) {
-                                               // Don't output state=loading for the startup module.
-                                               if ( $key !== 'startup' ) {
-                                                       $links['states'][$key] = 'loading';
-                                               }
-                                       }
-                               }
-
-                               if ( $group == 'noscript' ) {
-                                       $links['html'][] = Html::rawElement( 'noscript', [], $link );
-                               } else {
-                                       $links['html'][] = $link;
-                               }
-                       }
-               }
-
-               return $links;
+               return ResourceLoaderClientHtml::makeLoad(
+                       $this->getRlClientContext(),
+                       (array)$modules,
+                       $only,
+                       $extraQuery
+               );
        }
 
        /**
-        * Build html output from an array of links from makeResourceLoaderLink.
-        * @param array $links
+        * Combine WrappedString chunks and filter out empty ones
+        *
+        * @param array $chunks
         * @return string|WrappedStringList HTML
         */
-       protected static function getHtmlFromLoaderLinks( array $links ) {
-               $html = [];
-               $states = [];
-               foreach ( $links as $link ) {
-                       if ( !is_array( $link ) ) {
-                               $html[] = $link;
-                       } else {
-                               $html = array_merge( $html, $link['html'] );
-                               $states += $link['states'];
-                       }
-               }
+       protected static function combineWrappedStrings( array $chunks ) {
                // Filter out empty values
-               $html = array_filter( $html, 'strlen' );
-
-               if ( $states ) {
-                       array_unshift( $html, ResourceLoader::makeInlineScript(
-                               ResourceLoader::makeLoaderStateScript( $states )
-                       ) );
-               }
-
-               return WrappedString::join( "\n", $html );
+               $chunks = array_filter( $chunks, 'strlen' );
+               return WrappedString::join( "\n", $chunks );
        }
 
-       /**
-        * JS stuff to put in the "<head>". This is the startup module, config
-        * vars and modules marked with position 'top'
-        *
-        * @return string HTML fragment
-        */
-       function getHeadScripts() {
-               return $this->getInlineHeadScripts() . $this->getExternalHeadScripts();
-       }
-
-       /**
-        * <script src="..."> tags for "<head>".This is the startup module
-        * and other modules marked with position 'top'.
-        *
-        * @return string|WrappedStringList HTML
-        */
-       function getExternalHeadScripts() {
-               // Startup - this provides the client with the module
-               // manifest and loads jquery and mediawiki base modules
-               $links = [];
-               $links[] = $this->makeResourceLoaderLink( 'startup', ResourceLoaderModule::TYPE_SCRIPTS );
-               return self::getHtmlFromLoaderLinks( $links );
+       /** @return bool */
+       private function isUserModulePreview() {
+               return $this->getConfig()->get( 'AllowUserJs' )
+                       && $this->getUser()->isLoggedIn()
+                       && $this->getTitle()
+                       && $this->getTitle()->isJsSubpage()
+                       && $this->userCanPreview();
        }
 
        /**
-        * Inline "<script>" tags to put in "<head>".
+        * JS stuff to put at the bottom of the `<body>`. These are modules with position 'bottom',
+        * legacy scripts ($this->mScripts), and user JS.
         *
         * @return string|WrappedStringList HTML
         */
-       function getInlineHeadScripts() {
-               $links = [];
-
-               // Client profile classes for <html>. Allows for easy hiding/showing of UI components.
-               // Must be done synchronously on every page to avoid flashes of wrong content.
-               // Note: This class distinguishes MediaWiki-supported JavaScript from the rest.
-               // The "rest" includes browsers that support JavaScript but not supported by our runtime.
-               // For the performance benefit of the majority, this is added unconditionally here and is
-               // then fixed up by the startup module for unsupported browsers.
-               $links[] = Html::inlineScript(
-                       'document.documentElement.className = document.documentElement.className'
-                       . '.replace( /(^|\s)client-nojs(\s|$)/, "$1client-js$2" );'
-               );
-
-               // Load config before anything else
-               $links[] = ResourceLoader::makeInlineScript(
-                       ResourceLoader::makeConfigSetScript( $this->getJSVars() )
-               );
-
-               // Load embeddable private modules before any loader links
-               // This needs to be TYPE_COMBINED so these modules are properly wrapped
-               // in mw.loader.implement() calls and deferred until mw.user is available
-               $embedScripts = [ 'user.options' ];
-               $links[] = $this->makeResourceLoaderLink(
-                       $embedScripts,
-                       ResourceLoaderModule::TYPE_COMBINED
-               );
-               // Separate user.tokens as otherwise caching will be allowed (T84960)
-               $links[] = $this->makeResourceLoaderLink(
-                       'user.tokens',
-                       ResourceLoaderModule::TYPE_COMBINED
-               );
-
-               // Modules requests - let the client calculate dependencies and batch requests as it likes
-               // Only load modules that have marked themselves for loading at the top
-               $modules = $this->getModules( true, 'top' );
-               if ( $modules ) {
-                       $links[] = ResourceLoader::makeInlineScript(
-                               Xml::encodeJsCall( 'mw.loader.load', [ $modules ] )
-                       );
+       public function getBottomScripts() {
+               $chunks = [];
+               $chunks[] = $this->getRlClient()->getBodyHtml();
+
+               // Legacy non-ResourceLoader scripts
+               $chunks[] = $this->mScripts;
+
+               // Exempt 'user' module
+               // - May need excludepages for live preview. (T28283)
+               // - Must use TYPE_COMBINED so its response is handled by mw.loader.implement() which
+               //   ensures execution is scheduled after the "site" module.
+               // - Don't load if module state is already resolved as "ready".
+               if ( $this->rlUserModuleState === 'loading' ) {
+                       if ( $this->isUserModulePreview() ) {
+                               $chunks[] = $this->makeResourceLoaderLink( 'user', ResourceLoaderModule::TYPE_COMBINED,
+                                       [ 'excludepage' => $this->getTitle()->getPrefixedDBkey() ]
+                               );
+                               $chunks[] = ResourceLoader::makeInlineScript(
+                                       Xml::encodeJsCall( 'mw.loader.using', [
+                                               [ 'user', 'site' ],
+                                               new XmlJsCode(
+                                                       'function () {'
+                                                               . Xml::encodeJsCall( '$.globalEval', [
+                                                                       $this->getRequest()->getText( 'wpTextbox1' )
+                                                               ] )
+                                                               . '}'
+                                               )
+                                       ] )
+                               );
+                               // FIXME: If the user is previewing, say, ./vector.js, his ./common.js will be loaded
+                               // asynchronously and may arrive *after* the inline script here. So the previewed code
+                               // may execute before ./common.js runs. Normally, ./common.js runs before ./vector.js.
+                               // Similarly, when previewing ./common.js and the user module does arrive first,
+                               // it will arrive without common.js and the inline script runs after.
+                               // Thus running common after the excluded subpage.
+                       } else {
+                               // Load normally
+                               $chunks[] = $this->makeResourceLoaderLink( 'user', ResourceLoaderModule::TYPE_COMBINED );
+                       }
                }
 
-               // "Scripts only" modules marked for top inclusion
-               $links[] = $this->makeResourceLoaderLink(
-                       $this->getModuleScripts( true, 'top' ),
-                       ResourceLoaderModule::TYPE_SCRIPTS
+               $chunks[] = ResourceLoader::makeInlineScript(
+                       ResourceLoader::makeConfigSetScript(
+                               [ 'wgPageParseReport' => $this->limitReportData ],
+                               true
+                       )
                );
 
-               return self::getHtmlFromLoaderLinks( $links );
-       }
-
-       /**
-        * JS stuff to put at the 'bottom', which goes at the bottom of the `<body>`.
-        * These are modules marked with position 'bottom', legacy scripts ($this->mScripts),
-        * site JS, and user JS.
-        *
-        * @param bool $unused Previously used to let this method change its output based
-        *  on whether it was called by getExternalHeadScripts() or getBottomScripts().
-        * @return string|WrappedStringList HTML
-        */
-       function getScriptsForBottomQueue( $unused = null ) {
-               // Scripts "only" requests marked for bottom inclusion
-               // If we're in the <head>, use load() calls rather than <script src="..."> tags
-               $links = [];
-
-               $links[] = $this->makeResourceLoaderLink( $this->getModuleScripts( true, 'bottom' ),
-                       ResourceLoaderModule::TYPE_SCRIPTS
-               );
-
-               // Modules requests - let the client calculate dependencies and batch requests as it likes
-               // Only load modules that have marked themselves for loading at the bottom
-               $modules = $this->getModules( true, 'bottom' );
-               if ( $modules ) {
-                       $links[] = ResourceLoader::makeInlineScript(
-                               Xml::encodeJsCall( 'mw.loader.load', [ $modules ] )
-                       );
-               }
-
-               // Legacy Scripts
-               $links[] = $this->mScripts;
-
-               // Add user JS if enabled
-               // This must use TYPE_COMBINED instead of only=scripts so that its request is handled by
-               // mw.loader.implement() which ensures that execution is scheduled after the "site" module.
-               if ( $this->getConfig()->get( 'AllowUserJs' )
-                       && $this->getUser()->isLoggedIn()
-                       && $this->getTitle()
-                       && $this->getTitle()->isJsSubpage()
-                       && $this->userCanPreview()
-               ) {
-                       // We're on a preview of a JS subpage. Exclude this page from the user module (T28283)
-                       // and include the draft contents as a raw script instead.
-                       $links[] = $this->makeResourceLoaderLink( 'user', ResourceLoaderModule::TYPE_COMBINED,
-                               [ 'excludepage' => $this->getTitle()->getPrefixedDBkey() ]
-                       );
-                       // Load the previewed JS
-                       $links[] = ResourceLoader::makeInlineScript(
-                               Xml::encodeJsCall( 'mw.loader.using', [
-                                       [ 'user', 'site' ],
-                                       new XmlJsCode(
-                                               'function () {'
-                                                       . Xml::encodeJsCall( '$.globalEval', [
-                                                               $this->getRequest()->getText( 'wpTextbox1' )
-                                                       ] )
-                                                       . '}'
-                                       )
-                               ] )
-                       );
-
-                       // FIXME: If the user is previewing, say, ./vector.js, his ./common.js will be loaded
-                       // asynchronously and may arrive *after* the inline script here. So the previewed code
-                       // may execute before ./common.js runs. Normally, ./common.js runs before ./vector.js.
-                       // Similarly, when previewing ./common.js and the user module does arrive first,
-                       // it will arrive without common.js and the inline script runs after.
-                       // Thus running common after the excluded subpage.
-               } else {
-                       // Include the user module normally, i.e., raw to avoid it being wrapped in a closure.
-                       $links[] = $this->makeResourceLoaderLink( 'user', ResourceLoaderModule::TYPE_COMBINED );
-               }
-
-               return self::getHtmlFromLoaderLinks( $links );
-       }
-
-       /**
-        * JS stuff to put at the bottom of the "<body>"
-        * @return string
-        */
-       function getBottomScripts() {
-               return $this->getScriptsForBottomQueue() .
-                       ResourceLoader::makeInlineScript(
-                               ResourceLoader::makeConfigSetScript(
-                                       [ 'wgPageParseReport' => $this->limitReportData ],
-                                       true
-                               )
-                       );
+               return self::combineWrappedStrings( $chunks );
        }
 
        /**
@@ -3626,79 +3402,76 @@ class OutputPage extends ContextSource {
        }
 
        /**
-        * Build a set of "<link>" elements for stylesheets specified in the $this->styles array.
+        * Build exempt modules and legacy non-ResourceLoader styles.
         *
         * @return string|WrappedStringList HTML
         */
-       public function buildCssLinks() {
+       protected function buildExemptModules() {
                global $wgContLang;
 
-               $this->getSkin()->setupSkinUserCss( $this );
-
-               // Add ResourceLoader styles
-               // Split the styles into these groups
-               $styles = [
-                       'other' => [],
-                       'user' => [],
-                       'site' => [],
-                       'private' => [],
-                       'noscript' => []
-               ];
-               $links = [];
-               $otherTags = []; // Tags to append after the normal <link> tags
                $resourceLoader = $this->getResourceLoader();
+               $chunks = [];
+               // Things that should be appended after the other link and style chunks
+               $append = [];
+               $moduleStyles = [
+                       'site.styles',
+                       'noscript'
+               ];
 
-               $moduleStyles = $this->getModuleStyles();
-
-               // Per-site custom styles
-               $moduleStyles[] = 'site.styles';
-               $moduleStyles[] = 'noscript';
-
-               // Per-user custom styles
+               // Exempt 'user' styles module.
+               // - May need excludepages for live preview.
+               // - Position after ResourceLoaderDynamicStyles marker
                if ( $this->getConfig()->get( 'AllowUserCss' ) && $this->getTitle()->isCssSubpage()
                        && $this->userCanPreview()
                ) {
-                       // We're on a preview of a CSS subpage
-                       // Exclude this page from the user module in case it's in there (bug 26283)
-                       $link = $this->makeResourceLoaderLink( 'user.styles', ResourceLoaderModule::TYPE_STYLES,
+                       $append[] = $this->makeResourceLoaderLink(
+                               'user.styles',
+                               ResourceLoaderModule::TYPE_STYLES,
                                [ 'excludepage' => $this->getTitle()->getPrefixedDBkey() ]
                        );
-                       $otherTags = array_merge( $otherTags, $link['html'] );
 
-                       // Load the previewed CSS
-                       // If needed, Janus it first. This is user-supplied CSS, so it's
-                       // assumed to be right for the content language directionality.
+                       // Load the previewed CSS. Janus it if needed.
+                       // User-supplied CSS is assumed to in the wiki's content language.
                        $previewedCSS = $this->getRequest()->getText( 'wpTextbox1' );
                        if ( $this->getLanguage()->getDir() !== $wgContLang->getDir() ) {
                                $previewedCSS = CSSJanus::transform( $previewedCSS, true, false );
                        }
-                       $otherTags[] = Html::inlineStyle( $previewedCSS );
+                       $append[] = Html::inlineStyle( $previewedCSS );
                } else {
-                       // Load the user styles normally
-                       $moduleStyles[] = 'user.styles';
+                       $module = $this->getResourceLoader()->getModule( 'user.styles' );
+                       if ( !$module->isKnownEmpty( $this->getRlClientContext() ) ) {
+                               // Load styles normally
+                               $moduleStyles[] = 'user.styles';
+                       }
                }
 
-               // Per-user preference styles
+               // Exempt 'user.cssprefs' module
+               // - Position after ResourceLoaderDynamicStyles marker
                $moduleStyles[] = 'user.cssprefs';
 
+               $groups = [
+                       'other' => [],
+                       'site' => [],
+                       'noscript' => [],
+                       'private' => [],
+                       'user' => [],
+               ];
                foreach ( $moduleStyles as $name ) {
                        $module = $resourceLoader->getModule( $name );
-                       if ( !$module ) {
+                       if ( !$module || $module->isKnownEmpty( $this->getRlClientContext() ) ) {
+                               // E.g. Don't output empty <styles> for user.cssprefs
                                continue;
                        }
                        if ( $name === 'site.styles' ) {
-                               // HACK: The site module shouldn't be fragmented with a cache group and
-                               // http request. But in order to ensure its styles are separated and after the
-                               // ResourceLoaderDynamicStyles marker, pretend it is in a group called 'site'.
-                               // The scripts remain ungrouped and rides the bottom queue.
-                               $styles['site'][] = $name;
+                               // HACK: Technically, the 'site.styles' module isn't in a separate request group.
+                               // But, in order to ensure its styles are in the right position after the marker,
+                               // pretend it's in a group called 'site'.
+                               $groups['site'][] = $name;
                                continue;
                        }
                        $group = $module->getGroup();
-                       // Modules in groups other than the ones needing special treatment
-                       // (see $styles assignment)
-                       // will be placed in the "other" style category.
-                       $styles[isset( $styles[$group] ) ? $group : 'other'][] = $name;
+                       // Use "other" in case. All exempt modules are in one of the known groups though.
+                       $groups[isset( $groups[$group] ) ? $group : 'other'][] = $name;
                }
 
                // We want site, private and user styles to override dynamically added
@@ -3706,33 +3479,23 @@ class OutputPage extends ContextSource {
                // statically added styles from other modules. So the order has to be
                // other, dynamic, site, private, user. Add statically added styles for
                // other modules
-               $links[] = $this->makeResourceLoaderLink(
-                       $styles['other'],
-                       ResourceLoaderModule::TYPE_STYLES
-               );
-               // Add normal styles added through addStyle()/addInlineStyle() here
-               $links[] = implode( '', $this->buildCssLinksArray() ) . $this->mInlineStyles;
-               // Add marker tag to mark the place where the client-side
-               // loader should inject dynamic styles
-               // We use a <meta> tag with a made-up name for this because that's valid HTML
-               $links[] = Html::element(
+
+               // Add legacy styles added through addStyle()/addInlineStyle() here
+               $chunks[] = implode( '', $this->buildCssLinksArray() ) . $this->mInlineStyles;
+
+               // Client-side mw.loader will inject dynamic styles before this marker.
+               $chunks[] = Html::element(
                        'meta',
                        [ 'name' => 'ResourceLoaderDynamicStyles', 'content' => '' ]
                );
 
-               // Add site-specific and user-specific styles
-               // 'private' at present only contains user.options, so put that before 'user'
-               // Any future private modules will likely have a similar user-specific character
-               foreach ( [ 'site', 'noscript', 'private', 'user' ] as $group ) {
-                       $links[] = $this->makeResourceLoaderLink( $styles[$group],
+               foreach ( [ 'other', 'site', 'noscript', 'private', 'user' ] as $group ) {
+                       $chunks[] = $this->makeResourceLoaderLink( $groups[$group],
                                ResourceLoaderModule::TYPE_STYLES
                        );
                }
 
-               // Add stuff in $otherTags (previewed user CSS if applicable)
-               $links[] = implode( '', $otherTags );
-
-               return self::getHtmlFromLoaderLinks( $links );
+               return self::combineWrappedStrings( array_merge( $chunks, $append ) );
        }
 
        /**
index 3083a8d..70addfc 100644 (file)
@@ -207,8 +207,9 @@ class Preferences {
         * @return void
         */
        static function profilePreferences( $user, IContextSource $context, &$defaultPreferences ) {
-               global $wgAuth, $wgContLang, $wgParser, $wgDisableAuthManager;
+               global $wgContLang, $wgParser;
 
+               $authManager = AuthManager::singleton();
                $config = $context->getConfig();
                // retrieving user name for GENDER and misc.
                $userName = $user->getName();
@@ -283,21 +284,19 @@ class Preferences {
                $canEditPrivateInfo = $user->isAllowed( 'editmyprivateinfo' );
 
                // Actually changeable stuff
-               $realnameChangeAllowed = $wgDisableAuthManager ? $wgAuth->allowPropChange( 'realname' )
-                       : AuthManager::singleton()->allowsPropertyChange( 'realname' );
                $defaultPreferences['realname'] = [
                        // (not really "private", but still shouldn't be edited without permission)
-                       'type' => $canEditPrivateInfo && $realnameChangeAllowed ? 'text' : 'info',
+                       'type' => $canEditPrivateInfo && $authManager->allowsPropertyChange( 'realname' )
+                               ? 'text' : 'info',
                        'default' => $user->getRealName(),
                        'section' => 'personal/info',
                        'label-message' => 'yourrealname',
                        'help-message' => 'prefs-help-realname',
                ];
 
-               $allowPasswordChange = $wgDisableAuthManager ? $wgAuth->allowPasswordChange()
-                       : AuthManager::singleton()->allowsAuthenticationDataChange(
-                               new PasswordAuthenticationRequest(), false )->isGood();
-               if ( $canEditPrivateInfo && $allowPasswordChange ) {
+               if ( $canEditPrivateInfo && $authManager->allowsAuthenticationDataChange(
+                       new PasswordAuthenticationRequest(), false )->isGood()
+               ) {
                        $link = Linker::link( SpecialPage::getTitleFor( 'ChangePassword' ),
                                $context->msg( 'prefs-resetpass' )->escaped(), [],
                                [ 'returnto' => SpecialPage::getTitleFor( 'Preferences' )->getPrefixedText() ] );
@@ -418,10 +417,8 @@ class Preferences {
                        'default' => $oldsigHTML,
                        'section' => 'personal/signature',
                ];
-               $nicknameChangeAllowed = $wgDisableAuthManager ? $wgAuth->allowPropChange( 'nickname' )
-                       : AuthManager::singleton()->allowsPropertyChange( 'nickname' );
                $defaultPreferences['nickname'] = [
-                       'type' => $nicknameChangeAllowed ? 'text' : 'info',
+                       'type' => $authManager->allowsPropertyChange( 'nickname' ) ? 'text' : 'info',
                        'maxlength' => $config->get( 'MaxSigChars' ),
                        'label-message' => 'yournick',
                        'validation-callback' => [ 'Preferences', 'validateSignature' ],
@@ -450,9 +447,7 @@ class Preferences {
                                }
 
                                $emailAddress = $user->getEmail() ? htmlspecialchars( $user->getEmail() ) : '';
-                               $emailChangeAllowed = $wgDisableAuthManager ? $wgAuth->allowPropChange( 'emailaddress' )
-                                       : AuthManager::singleton()->allowsPropertyChange( 'emailaddress' );
-                               if ( $canEditPrivateInfo && $emailChangeAllowed ) {
+                               if ( $canEditPrivateInfo && $authManager->allowsPropertyChange( 'emailaddress' ) ) {
                                        $link = Linker::link(
                                                SpecialPage::getTitleFor( 'ChangeEmail' ),
                                                $context->msg( $user->getEmail() ? 'prefs-changeemail' : 'prefs-setemail' )->escaped(),
index 6c5de90..cbe4e2e 100644 (file)
@@ -452,22 +452,6 @@ if ( $wgProfileOnly ) {
        $wgDebugLogFile = '';
 }
 
-// Disable AuthManager API modules if $wgDisableAuthManager
-if ( $wgDisableAuthManager ) {
-       $wgAPIModules += [
-               'clientlogin' => 'ApiDisabled',
-               'createaccount' => 'ApiCreateAccount', // Use the non-AuthManager version
-               'linkaccount' => 'ApiDisabled',
-               'unlinkaccount' => 'ApiDisabled',
-               'changeauthenticationdata' => 'ApiDisabled',
-               'removeauthenticationdata' => 'ApiDisabled',
-               'resetpassword' => 'ApiDisabled',
-       ];
-       $wgAPIMetaModules += [
-               'authmanagerinfo' => 'ApiQueryDisabled',
-       ];
-}
-
 // Backwards compatibility with old password limits
 if ( $wgMinimalPasswordLength !== false ) {
        $wgPasswordPolicy['policies']['default']['MinimalPasswordLength'] = $wgMinimalPasswordLength;
@@ -711,12 +695,10 @@ $wgContLang->initContLang();
 $wgRequest->interpolateTitle();
 
 if ( !is_object( $wgAuth ) ) {
-       $wgAuth = $wgDisableAuthManager ? new AuthPlugin : new MediaWiki\Auth\AuthManagerAuthPlugin;
+       $wgAuth = new MediaWiki\Auth\AuthManagerAuthPlugin;
        Hooks::run( 'AuthPluginSetup', [ &$wgAuth ] );
 }
-if ( !$wgDisableAuthManager &&
-       $wgAuth && !$wgAuth instanceof MediaWiki\Auth\AuthManagerAuthPlugin
-) {
+if ( $wgAuth && !$wgAuth instanceof MediaWiki\Auth\AuthManagerAuthPlugin ) {
        MediaWiki\Auth\AuthManager::singleton()->forcePrimaryAuthenticationProviders( [
                new MediaWiki\Auth\TemporaryPasswordPrimaryAuthenticationProvider( [
                        'authoritative' => false,
@@ -852,17 +834,13 @@ if ( !defined( 'MW_NO_SESSION' ) && !$wgCommandLineMode ) {
        $sessionUser = MediaWiki\Session\SessionManager::getGlobalSession()->getUser();
        if ( $sessionUser->getId() === 0 && User::isValidUserName( $sessionUser->getName() ) ) {
                $ps_autocreate = Profiler::instance()->scopedProfileIn( $fname . '-autocreate' );
-               if ( $wgDisableAuthManager ) {
-                       $res = MediaWiki\Session\SessionManager::autoCreateUser( $sessionUser );
-               } else {
-                       $res = MediaWiki\Auth\AuthManager::singleton()->autoCreateUser(
-                               $sessionUser,
-                               MediaWiki\Auth\AuthManager::AUTOCREATE_SOURCE_SESSION,
-                               true
-                       );
-               }
+               $res = MediaWiki\Auth\AuthManager::singleton()->autoCreateUser(
+                       $sessionUser,
+                       MediaWiki\Auth\AuthManager::AUTOCREATE_SOURCE_SESSION,
+                       true
+               );
                Profiler::instance()->scopedProfileOut( $ps_autocreate );
-               \MediaWiki\Logger\LoggerFactory::getInstance( 'authmanager' )->info( 'Autocreation attempt', [
+               \MediaWiki\Logger\LoggerFactory::getInstance( 'authevents' )->info( 'Autocreation attempt', [
                        'event' => 'autocreate',
                        'status' => $res,
                ] );
index 6c536dd..03b4b8c 100644 (file)
@@ -24,7 +24,7 @@
  * Static accessor class for site_stats and related things
  */
 class SiteStats {
-       /** @var bool|ResultWrapper */
+       /** @var bool|stdClass */
        private static $row;
 
        /** @var bool */
@@ -62,7 +62,7 @@ class SiteStats {
        }
 
        /**
-        * @return bool|ResultWrapper
+        * @return bool|stdClass
         */
        static function loadAndLazyInit() {
                global $wgMiserMode;
@@ -96,7 +96,7 @@ class SiteStats {
 
        /**
         * @param IDatabase $db
-        * @return bool|ResultWrapper
+        * @return bool|stdClass
         */
        static function doLoad( $db ) {
                return $db->selectRow( 'site_stats', [
@@ -107,7 +107,7 @@ class SiteStats {
                                'ss_users',
                                'ss_active_users',
                                'ss_images',
-                       ], false, __METHOD__ );
+                       ], [], __METHOD__ );
        }
 
        /**
index ea42768..ed445cc 100644 (file)
@@ -2319,8 +2319,8 @@ class Title implements LinkTarget {
                        # If the user is allowed to read pages, he is allowed to read all pages
                        $whitelisted = true;
                } elseif ( $this->isSpecial( 'Userlogin' )
-                       || $this->isSpecial( 'ChangePassword' )
                        || $this->isSpecial( 'PasswordReset' )
+                       || $this->isSpecial( 'Userlogout' )
                ) {
                        # Always grant access to the login page.
                        # Even anons need to be able to log in.
index 7be2aa7..ea66900 100644 (file)
@@ -671,7 +671,7 @@ class InfoAction extends FormlessAction {
 
                return ObjectCache::getMainWANInstance()->getWithSetCallback(
                        self::getCacheKey( $page->getTitle(), $page->getLatest() ),
-                       86400 * 7,
+                       WANObjectCache::TTL_WEEK,
                        function ( $oldValue, &$ttl, &$setOpts ) use ( $page, $config, $fname ) {
                                $title = $page->getTitle();
                                $id = $title->getArticleID();
index 576533d..b2002ff 100644 (file)
  */
 
 /**
- * User-requested page cache purging.
- *
- * For users with 'purge', this will directly trigger the cache purging and
- * for users without that right, it will show a confirmation form.
+ * User-requested page cache purging
  *
  * @ingroup Actions
  */
@@ -48,10 +45,6 @@ class PurgeAction extends FormAction {
                return $this->page->doPurge();
        }
 
-       /**
-        * purge is slightly weird because it can be either formed or formless depending
-        * on user permissions
-        */
        public function show() {
                $this->setHeaders();
 
@@ -65,11 +58,7 @@ class PurgeAction extends FormAction {
                        return;
                }
 
-               if ( $user->isAllowed( 'purge' ) ) {
-                       // This will update the database immediately, even on HTTP GET.
-                       // Lots of uses may exist for this feature, so just ignore warnings.
-                       Profiler::instance()->getTransactionProfiler()->resetExpectations();
-
+               if ( $this->getRequest()->wasPosted() ) {
                        $this->redirectParams = wfArrayToCgi( array_diff_key(
                                $this->getRequest()->getQueryValues(),
                                [ 'title' => null, 'action' => null ]
index fe5675a..c970f93 100644 (file)
@@ -238,7 +238,7 @@ class ApiAuthManagerHelper {
                }
 
                $module = $this->module->getModuleName();
-               LoggerFactory::getInstance( 'authmanager' )->info( "$module API attempt", [
+               LoggerFactory::getInstance( 'authevents' )->info( "$module API attempt", [
                        'event' => $event,
                        'status' => $status,
                        'module' => $module,
diff --git a/includes/api/ApiCreateAccount.php b/includes/api/ApiCreateAccount.php
deleted file mode 100644 (file)
index 6a48610..0000000
+++ /dev/null
@@ -1,238 +0,0 @@
-<?php
-/**
- * Created on August 7, 2012
- *
- * Copyright © 2012 Tyler Romeo <tylerromeo@gmail.com>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- */
-use MediaWiki\Logger\LoggerFactory;
-
-/**
- * Unit to authenticate account registration attempts to the current wiki.
- *
- * @ingroup API
- * @deprecated since 1.27, only used when $wgDisableAuthManager is true
- */
-class ApiCreateAccount extends ApiBase {
-       public function execute() {
-               // If we're in a mode that breaks the same-origin policy, no tokens can
-               // be obtained
-               if ( $this->lacksSameOriginSecurity() ) {
-                       $this->dieUsage(
-                               'Cannot create account when the same-origin policy is not applied', 'aborted'
-                       );
-               }
-
-               // $loginForm->addNewaccountInternal will throw exceptions
-               // if wiki is read only (already handled by api), user is blocked or does not have rights.
-               // Use userCan in order to hit GlobalBlock checks (according to Special:userlogin)
-               $loginTitle = SpecialPage::getTitleFor( 'Userlogin' );
-               if ( !$loginTitle->userCan( 'createaccount', $this->getUser() ) ) {
-                       $this->dieUsage(
-                               'You do not have the right to create a new account',
-                               'permdenied-createaccount'
-                       );
-               }
-               if ( $this->getUser()->isBlockedFromCreateAccount() ) {
-                       $this->dieUsage(
-                               'You cannot create a new account because you are blocked',
-                               'blocked',
-                               0,
-                               [ 'blockinfo' => ApiQueryUserInfo::getBlockInfo( $this->getUser()->getBlock() ) ]
-                       );
-               }
-
-               $params = $this->extractRequestParams();
-
-               // Make sure session is persisted
-               MediaWiki\Session\SessionManager::getGlobalSession()->persist();
-
-               if ( $params['mailpassword'] && !$params['email'] ) {
-                       $this->dieUsageMsg( 'noemail' );
-               }
-
-               if ( $params['language'] && !Language::isSupportedLanguage( $params['language'] ) ) {
-                       $this->dieUsage( 'Invalid language parameter', 'langinvalid' );
-               }
-
-               $context = new DerivativeContext( $this->getContext() );
-               $context->setRequest( new DerivativeRequest(
-                       $this->getContext()->getRequest(),
-                       [
-                               'type' => 'signup',
-                               'uselang' => $params['language'],
-                               'wpName' => $params['name'],
-                               'wpPassword' => $params['password'],
-                               'wpRetype' => $params['password'],
-                               'wpDomain' => $params['domain'],
-                               'wpEmail' => $params['email'],
-                               'wpRealName' => $params['realname'],
-                               'wpCreateaccountToken' => $params['token'],
-                               'wpCreateaccount' => $params['mailpassword'] ? null : '1',
-                               'wpCreateaccountMail' => $params['mailpassword'] ? '1' : null
-                       ]
-               ) );
-
-               $loginForm = new LoginForm();
-               $loginForm->setContext( $context );
-               Hooks::run( 'AddNewAccountApiForm', [ $this, $loginForm ] );
-               $loginForm->load();
-
-               $status = $loginForm->addNewAccountInternal();
-               LoggerFactory::getInstance( 'authmanager' )->info( 'Account creation attempt via API', [
-                       'event' => 'accountcreation',
-                       'status' => $status,
-               ] );
-               $result = [];
-               if ( $status->isGood() ) {
-                       // Success!
-                       $user = $status->getValue();
-
-                       if ( $params['language'] ) {
-                               $user->setOption( 'language', $params['language'] );
-                       }
-
-                       if ( $params['mailpassword'] ) {
-                               // If mailpassword was set, disable the password and send an email.
-                               $user->setPassword( null );
-                               $status->merge( $loginForm->mailPasswordInternal(
-                                       $user,
-                                       false,
-                                       'createaccount-title',
-                                       'createaccount-text'
-                               ) );
-                       } elseif ( $this->getConfig()->get( 'EmailAuthentication' ) &&
-                               Sanitizer::validateEmail( $user->getEmail() )
-                       ) {
-                               // Send out an email authentication message if needed
-                               $status->merge( $user->sendConfirmationMail() );
-                       }
-
-                       // Save settings (including confirmation token)
-                       $user->saveSettings();
-
-                       Hooks::run( 'AddNewAccount', [ $user, $params['mailpassword'] ] );
-
-                       if ( $params['mailpassword'] ) {
-                               $logAction = 'byemail';
-                       } elseif ( $this->getUser()->isLoggedIn() ) {
-                               $logAction = 'create2';
-                       } else {
-                               $logAction = 'create';
-                       }
-                       $user->addNewUserLogEntry( $logAction, (string)$params['reason'] );
-
-                       // Add username, id, and token to result.
-                       $result['username'] = $user->getName();
-                       $result['userid'] = $user->getId();
-                       $result['token'] = $user->getToken();
-               }
-
-               $apiResult = $this->getResult();
-
-               if ( $status->hasMessage( 'sessionfailure' ) || $status->hasMessage( 'nocookiesfornew' ) ) {
-                       // Token was incorrect, so add it to result, but don't throw an exception
-                       // since not having the correct token is part of the normal
-                       // flow of events.
-                       $result['token'] = LoginForm::getCreateaccountToken()->toString();
-                       $result['result'] = 'NeedToken';
-                       $this->setWarning( 'Fetching a token via action=createaccount is deprecated. ' .
-                               'Use action=query&meta=tokens&type=createaccount instead.' );
-                       $this->logFeatureUsage( 'action=createaccount&!token' );
-               } elseif ( !$status->isOK() ) {
-                       // There was an error. Die now.
-                       $this->dieStatus( $status );
-               } elseif ( !$status->isGood() ) {
-                       // Status is not good, but OK. This means warnings.
-                       $result['result'] = 'Warning';
-
-                       // Add any warnings to the result
-                       $warnings = $status->getErrorsByType( 'warning' );
-                       if ( $warnings ) {
-                               foreach ( $warnings as &$warning ) {
-                                       ApiResult::setIndexedTagName( $warning['params'], 'param' );
-                               }
-                               ApiResult::setIndexedTagName( $warnings, 'warning' );
-                               $result['warnings'] = $warnings;
-                       }
-               } else {
-                       // Everything was fine.
-                       $result['result'] = 'Success';
-               }
-
-               // Give extensions a chance to modify the API result data
-               Hooks::run( 'AddNewAccountApiResult', [ $this, $loginForm, &$result ] );
-
-               $apiResult->addValue( null, 'createaccount', $result );
-       }
-
-       public function mustBePosted() {
-               return true;
-       }
-
-       public function isReadMode() {
-               return false;
-       }
-
-       public function isWriteMode() {
-               return true;
-       }
-
-       public function getAllowedParams() {
-               return [
-                       'name' => [
-                               ApiBase::PARAM_TYPE => 'user',
-                               ApiBase::PARAM_REQUIRED => true
-                       ],
-                       'password' => [
-                               ApiBase::PARAM_TYPE => 'password',
-                       ],
-                       'domain' => null,
-                       'token' => [
-                               ApiBase::PARAM_TYPE => 'string',
-                               ApiBase::PARAM_REQUIRED => false, // for BC
-                               ApiBase::PARAM_HELP_MSG => [ 'api-help-param-token', 'createaccount' ],
-                       ],
-                       'email' => [
-                               ApiBase::PARAM_TYPE => 'string',
-                               ApiBase::PARAM_REQUIRED => $this->getConfig()->get( 'EmailConfirmToEdit' ),
-                       ],
-                       'realname' => null,
-                       'mailpassword' => [
-                               ApiBase::PARAM_TYPE => 'boolean',
-                               ApiBase::PARAM_DFLT => false
-                       ],
-                       'reason' => null,
-                       'language' => null
-               ];
-       }
-
-       protected function getExamplesMessages() {
-               return [
-                       'action=createaccount&name=testuser&password=test123'
-                               => 'apihelp-createaccount-example-pass',
-                       'action=createaccount&name=testmailuser&mailpassword=true&reason=MyReason'
-                               => 'apihelp-createaccount-example-mail',
-               ];
-       }
-
-       public function getHelpUrls() {
-               return 'https://www.mediawiki.org/wiki/API:Account_creation';
-       }
-}
index 0e4c6e0..851252c 100644 (file)
@@ -42,9 +42,7 @@ class ApiLogin extends ApiBase {
        }
 
        protected function getDescriptionMessage() {
-               if ( $this->getConfig()->get( 'DisableAuthManager' ) ) {
-                       return 'apihelp-login-description-nonauthmanager';
-               } elseif ( $this->getConfig()->get( 'EnableBotPasswords' ) ) {
+               if ( $this->getConfig()->get( 'EnableBotPasswords' ) ) {
                        return 'apihelp-login-description';
                } else {
                        return 'apihelp-login-description-nobotpasswords';
@@ -117,92 +115,59 @@ class ApiLogin extends ApiBase {
                        } else {
                                $authRes = 'Failed';
                                $message = $status->getMessage();
-                               LoggerFactory::getInstance( 'authmanager' )->info(
+                               LoggerFactory::getInstance( 'authentication' )->info(
                                        'BotPassword login failed: ' . $status->getWikiText( false, false, 'en' )
                                );
                        }
                }
 
                if ( $authRes === false ) {
-                       if ( $this->getConfig()->get( 'DisableAuthManager' ) ) {
-                               // Non-AuthManager login
-                               $context->setRequest( new DerivativeRequest(
-                                       $this->getContext()->getRequest(),
-                                       [
-                                               'wpName' => $params['name'],
-                                               'wpPassword' => $params['password'],
-                                               'wpDomain' => $params['domain'],
-                                               'wpLoginToken' => $params['token'],
-                                               'wpRemember' => ''
-                                       ]
-                               ) );
-                               $loginForm = new LoginForm();
-                               $loginForm->setContext( $context );
-                               $authRes = $loginForm->authenticateUserData();
-                               $loginType = 'LoginForm';
-
-                               switch ( $authRes ) {
-                                       case LoginForm::SUCCESS:
-                                               $authRes = 'Success';
-                                               break;
-                                       case LoginForm::NEED_TOKEN:
-                                               $authRes = 'NeedToken';
-                                               break;
-                               }
-                       } else {
-                               // Simplified AuthManager login, for backwards compatibility
-                               $manager = AuthManager::singleton();
-                               $reqs = AuthenticationRequest::loadRequestsFromSubmission(
-                                       $manager->getAuthenticationRequests( AuthManager::ACTION_LOGIN, $this->getUser() ),
-                                       [
-                                               'username' => $params['name'],
-                                               'password' => $params['password'],
-                                               'domain' => $params['domain'],
-                                               'rememberMe' => true,
-                                       ]
-                               );
-                               $res = AuthManager::singleton()->beginAuthentication( $reqs, 'null:' );
-                               switch ( $res->status ) {
-                                       case AuthenticationResponse::PASS:
-                                               if ( $this->getConfig()->get( 'EnableBotPasswords' ) ) {
-                                                       $warn = 'Main-account login via action=login is deprecated and may stop working ' .
-                                                               'without warning.';
-                                                       $warn .= ' To continue login with action=login, see [[Special:BotPasswords]].';
-                                                       $warn .= ' To safely continue using main-account login, see action=clientlogin.';
-                                               } else {
-                                                       $warn = 'Login via action=login is deprecated and may stop working without warning.';
-                                                       $warn .= ' To safely log in, see action=clientlogin.';
-                                               }
-                                               $this->setWarning( $warn );
-                                               $authRes = 'Success';
-                                               $loginType = 'AuthManager';
-                                               break;
-
-                                       case AuthenticationResponse::FAIL:
-                                               // Hope it's not a PreAuthenticationProvider that failed...
-                                               $authRes = 'Failed';
-                                               $message = $res->message;
-                                               \MediaWiki\Logger\LoggerFactory::getInstance( 'authentication' )
-                                                       ->info( __METHOD__ . ': Authentication failed: ' . $message->plain() );
-                                               break;
-
-                                       default:
-                                               $authRes = 'Aborted';
-                                               break;
-                               }
+                       // Simplified AuthManager login, for backwards compatibility
+                       $manager = AuthManager::singleton();
+                       $reqs = AuthenticationRequest::loadRequestsFromSubmission(
+                               $manager->getAuthenticationRequests( AuthManager::ACTION_LOGIN, $this->getUser() ),
+                               [
+                                       'username' => $params['name'],
+                                       'password' => $params['password'],
+                                       'domain' => $params['domain'],
+                                       'rememberMe' => true,
+                               ]
+                       );
+                       $res = AuthManager::singleton()->beginAuthentication( $reqs, 'null:' );
+                       switch ( $res->status ) {
+                               case AuthenticationResponse::PASS:
+                                       if ( $this->getConfig()->get( 'EnableBotPasswords' ) ) {
+                                               $warn = 'Main-account login via action=login is deprecated and may stop working ' .
+                                                       'without warning.';
+                                               $warn .= ' To continue login with action=login, see [[Special:BotPasswords]].';
+                                               $warn .= ' To safely continue using main-account login, see action=clientlogin.';
+                                       } else {
+                                               $warn = 'Login via action=login is deprecated and may stop working without warning.';
+                                               $warn .= ' To safely log in, see action=clientlogin.';
+                                       }
+                                       $this->setWarning( $warn );
+                                       $authRes = 'Success';
+                                       $loginType = 'AuthManager';
+                                       break;
+
+                               case AuthenticationResponse::FAIL:
+                                       // Hope it's not a PreAuthenticationProvider that failed...
+                                       $authRes = 'Failed';
+                                       $message = $res->message;
+                                       \MediaWiki\Logger\LoggerFactory::getInstance( 'authentication' )
+                                               ->info( __METHOD__ . ': Authentication failed: ' . $message->plain() );
+                                       break;
+
+                               default:
+                                       $authRes = 'Aborted';
+                                       break;
                        }
                }
 
                $result['result'] = $authRes;
                switch ( $authRes ) {
                        case 'Success':
-                               if ( $this->getConfig()->get( 'DisableAuthManager' ) ) {
-                                       $user = $context->getUser();
-                                       $this->getContext()->setUser( $user );
-                                       $user->setCookies( $this->getRequest(), null, true );
-                               } else {
-                                       $user = $session->getUser();
-                               }
+                               $user = $session->getUser();
 
                                ApiQueryInfo::resetTokenCache();
 
@@ -252,65 +217,6 @@ class ApiLogin extends ApiBase {
                                }
                                break;
 
-                       // Results from LoginForm for when $wgDisableAuthManager is true
-                       case LoginForm::WRONG_TOKEN:
-                               $result['result'] = 'WrongToken';
-                               break;
-
-                       case LoginForm::NO_NAME:
-                               $result['result'] = 'NoName';
-                               break;
-
-                       case LoginForm::ILLEGAL:
-                               $result['result'] = 'Illegal';
-                               break;
-
-                       case LoginForm::WRONG_PLUGIN_PASS:
-                               $result['result'] = 'WrongPluginPass';
-                               break;
-
-                       case LoginForm::NOT_EXISTS:
-                               $result['result'] = 'NotExists';
-                               break;
-
-                       // bug 20223 - Treat a temporary password as wrong. Per SpecialUserLogin:
-                       // The e-mailed temporary password should not be used for actual logins.
-                       case LoginForm::RESET_PASS:
-                       case LoginForm::WRONG_PASS:
-                               $result['result'] = 'WrongPass';
-                               break;
-
-                       case LoginForm::EMPTY_PASS:
-                               $result['result'] = 'EmptyPass';
-                               break;
-
-                       case LoginForm::CREATE_BLOCKED:
-                               $result['result'] = 'CreateBlocked';
-                               $result['details'] = 'Your IP address is blocked from account creation';
-                               $block = $context->getUser()->getBlock();
-                               if ( $block ) {
-                                       $result = array_merge( $result, ApiQueryUserInfo::getBlockInfo( $block ) );
-                               }
-                               break;
-
-                       case LoginForm::THROTTLED:
-                               $result['result'] = 'Throttled';
-                               $result['wait'] = intval( $loginForm->mThrottleWait );
-                               break;
-
-                       case LoginForm::USER_BLOCKED:
-                               $result['result'] = 'Blocked';
-                               $block = User::newFromName( $params['name'] )->getBlock();
-                               if ( $block ) {
-                                       $result = array_merge( $result, ApiQueryUserInfo::getBlockInfo( $block ) );
-                               }
-                               break;
-
-                       case LoginForm::ABORTED:
-                               $result['result'] = 'Aborted';
-                               $result['reason'] = $loginForm->mAbortLoginErrorMsg;
-                               break;
-
                        default:
                                ApiBase::dieDebug( __METHOD__, "Unhandled case value: {$authRes}" );
                }
@@ -320,7 +226,7 @@ class ApiLogin extends ApiBase {
                if ( $loginType === 'LoginForm' && isset( LoginForm::$statusCodes[$authRes] ) ) {
                        $authRes = LoginForm::$statusCodes[$authRes];
                }
-               LoggerFactory::getInstance( 'authmanager' )->info( 'Login attempt', [
+               LoggerFactory::getInstance( 'authevents' )->info( 'Login attempt', [
                        'event' => 'login',
                        'successful' => $authRes === 'Success',
                        'loginType' => $loginType,
@@ -329,8 +235,7 @@ class ApiLogin extends ApiBase {
        }
 
        public function isDeprecated() {
-               return !$this->getConfig()->get( 'DisableAuthManager' ) &&
-                       !$this->getConfig()->get( 'EnableBotPasswords' );
+               return !$this->getConfig()->get( 'EnableBotPasswords' );
        }
 
        public function mustBePosted() {
index 5afb66f..cfc1e46 100644 (file)
@@ -261,7 +261,7 @@ class ApiQueryUsers extends ApiQueryBase {
                                        }
                                } else {
                                        $data[$u]['missing'] = true;
-                                       if ( isset( $this->prop['cancreate'] ) && !$this->getConfig()->get( 'DisableAuthManager' ) ) {
+                                       if ( isset( $this->prop['cancreate'] ) ) {
                                                $status = MediaWiki\Auth\AuthManager::singleton()->canCreateAccount( $u );
                                                $data[$u]['cancreate'] = $status->isGood();
                                                if ( !$status->isGood() ) {
@@ -307,7 +307,7 @@ class ApiQueryUsers extends ApiQueryBase {
        }
 
        public function getAllowedParams() {
-               $ret = [
+               return [
                        'prop' => [
                                ApiBase::PARAM_ISMULTI => true,
                                ApiBase::PARAM_TYPE => [
@@ -320,6 +320,7 @@ class ApiQueryUsers extends ApiQueryBase {
                                        'emailable',
                                        'gender',
                                        'centralids',
+                                       'cancreate',
                                        // When adding a prop, consider whether it should be added
                                        // to self::$publicProps
                                ],
@@ -336,10 +337,6 @@ class ApiQueryUsers extends ApiQueryBase {
                                ApiBase::PARAM_ISMULTI => true
                        ],
                ];
-               if ( !$this->getConfig()->get( 'DisableAuthManager' ) ) {
-                       $ret['prop'][ApiBase::PARAM_TYPE][] = 'cancreate';
-               }
-               return $ret;
        }
 
        protected function getExamplesMessages() {
index 446a98c..297c0fb 100644 (file)
@@ -39,6 +39,7 @@ class ApiStashEdit extends ApiBase {
        const ERROR_PARSE = 'error_parse';
        const ERROR_CACHE = 'error_cache';
        const ERROR_UNCACHEABLE = 'uncacheable';
+       const ERROR_BUSY = 'busy';
 
        const PRESUME_FRESH_TTL_SEC = 30;
        const MAX_CACHE_TTL = 300; // 5 minutes
@@ -51,6 +52,7 @@ class ApiStashEdit extends ApiBase {
                        $this->dieUsage( 'This interface is not supported for bots', 'botsnotsupported' );
                }
 
+               $cache = ObjectCache::getLocalClusterInstance();
                $page = $this->getTitleOrPageId( $params );
                $title = $page->getTitle();
 
@@ -60,8 +62,23 @@ class ApiStashEdit extends ApiBase {
                        $this->dieUsage( 'Unsupported content model/format', 'badmodelformat' );
                }
 
-               // Trim and fix newlines so the key SHA1's match (see RequestContext::getText())
-               $text = rtrim( str_replace( "\r\n", "\n", $params['text'] ) );
+               if ( strlen( $params['stashedtexthash'] ) ) {
+                       // Load from cache since the client indicates the text is the same as last stash
+                       $textHash = $params['stashedtexthash'];
+                       $textKey = $cache->makeKey( 'stashedit', 'text', $textHash );
+                       $text = $cache->get( $textKey );
+                       if ( !is_string( $text ) ) {
+                               $this->dieUsage( 'No stashed text found with the given hash', 'missingtext' );
+                       }
+               } elseif ( $params['text'] !== null ) {
+                       // Trim and fix newlines so the key SHA1's match (see WebRequest::getText())
+                       $text = rtrim( str_replace( "\r\n", "\n", $params['text'] ) );
+                       $textHash = sha1( $text );
+               } else {
+                       $this->dieUsage(
+                               'The text or stashedtexthash parameter must be given', 'missingtextparam' );
+               }
+
                $textContent = ContentHandler::makeContent(
                        $text, $title, $params['contentmodel'], $params['contentformat'] );
 
@@ -113,24 +130,24 @@ class ApiStashEdit extends ApiBase {
                // The user will abort the AJAX request by pressing "save", so ignore that
                ignore_user_abort( true );
 
-               // Use the master DB for fast blocking locks
-               $dbw = wfGetDB( DB_MASTER );
-
-               // Get a key based on the source text, format, and user preferences
-               $key = self::getStashKey( $title, $content, $user );
-               // De-duplicate requests on the same key
                if ( $user->pingLimiter( 'stashedit' ) ) {
                        $status = 'ratelimited';
-               } elseif ( $dbw->lock( $key, __METHOD__, 1 ) ) {
-                       $status = self::parseAndStash( $page, $content, $user, $params['summary'] );
-                       $dbw->unlock( $key, __METHOD__ );
                } else {
-                       $status = 'busy';
+                       $status = self::parseAndStash( $page, $content, $user, $params['summary'] );
+                       $textKey = $cache->makeKey( 'stashedit', 'text', $textHash );
+                       $cache->set( $textKey, $text, self::MAX_CACHE_TTL );
                }
 
                $this->getStats()->increment( "editstash.cache_stores.$status" );
 
-               $this->getResult()->addValue( null, $this->getModuleName(), [ 'status' => $status ] );
+               $this->getResult()->addValue(
+                       null,
+                       $this->getModuleName(),
+                       [
+                               'status' => $status,
+                               'texthash' => $textHash
+                       ]
+               );
        }
 
        /**
@@ -145,17 +162,41 @@ class ApiStashEdit extends ApiBase {
                $cache = ObjectCache::getLocalClusterInstance();
                $logger = LoggerFactory::getInstance( 'StashEdit' );
 
-               $format = $content->getDefaultFormat();
-               $editInfo = $page->prepareContentForEdit( $content, null, $user, $format, false );
                $title = $page->getTitle();
+               $key = self::getStashKey( $title, self::getContentHash( $content ), $user );
 
-               if ( $editInfo && $editInfo->output ) {
-                       $key = self::getStashKey( $title, $content, $user );
+               // Use the master DB for fast blocking locks
+               $dbw = wfGetDB( DB_MASTER );
+               if ( !$dbw->lock( $key, __METHOD__, 1 ) ) {
+                       // De-duplicate requests on the same key
+                       return self::ERROR_BUSY;
+               }
+               $unlocker = new ScopedCallback( function () use ( $dbw, $key ) {
+                       $dbw->unlock( $key, __METHOD__ );
+               } );
+
+               $cutoffTime = time() - self::PRESUME_FRESH_TTL_SEC;
+
+               // Reuse any freshly build matching edit stash cache
+               $editInfo = $cache->get( $key );
+               if ( $editInfo && wfTimestamp( TS_UNIX, $editInfo->timestamp ) >= $cutoffTime ) {
+                       $alreadyCached = true;
+               } else {
+                       $format = $content->getDefaultFormat();
+                       $editInfo = $page->prepareContentForEdit( $content, null, $user, $format, false );
+                       $alreadyCached = false;
+               }
 
+               if ( $editInfo && $editInfo->output ) {
                        // Let extensions add ParserOutput metadata or warm other caches
                        Hooks::run( 'ParserOutputStashForEdit',
                                [ $page, $content, $editInfo->output, $summary, $user ] );
 
+                       if ( $alreadyCached ) {
+                               $logger->debug( "Already cached parser output for key '$key' ('$title')." );
+                               return self::ERROR_NONE;
+                       }
+
                        list( $stashInfo, $ttl, $code ) = self::buildStashValue(
                                $editInfo->pstContent,
                                $editInfo->output,
@@ -207,7 +248,7 @@ class ApiStashEdit extends ApiBase {
                $logger = LoggerFactory::getInstance( 'StashEdit' );
                $stats = RequestContext::getMain()->getStats();
 
-               $key = self::getStashKey( $title, $content, $user );
+               $key = self::getStashKey( $title, self::getContentHash( $content ), $user );
                $editInfo = $cache->get( $key );
                if ( !is_object( $editInfo ) ) {
                        $start = microtime( true );
@@ -282,6 +323,20 @@ class ApiStashEdit extends ApiBase {
                return wfTimestampOrNull( TS_MW, $time );
        }
 
+       /**
+        * Get hash of the content, factoring in model/format
+        *
+        * @param Content $content
+        * @return string
+        */
+       private static function getContentHash( Content $content ) {
+               return sha1( implode( "\n", [
+                       $content->getModel(),
+                       $content->getDefaultFormat(),
+                       $content->serialize( $content->getDefaultFormat() )
+               ] ) );
+       }
+
        /**
         * Get the temporary prepared edit stash key for a user
         *
@@ -290,22 +345,19 @@ class ApiStashEdit extends ApiBase {
         *   - b) The parser output was made from the PST using cannonical matching options
         *
         * @param Title $title
-        * @param Content $content
+        * @param string $contentHash Result of getContentHash()
         * @param User $user User to get parser options from
         * @return string
         */
-       private static function getStashKey( Title $title, Content $content, User $user ) {
-               $hash = sha1( implode( ':', [
+       private static function getStashKey( Title $title, $contentHash, User $user ) {
+               return ObjectCache::getLocalClusterInstance()->makeKey(
+                       'prepared-edit',
+                       md5( $title->getPrefixedDBkey() ),
                        // Account for the edit model/text
-                       $content->getModel(),
-                       $content->getDefaultFormat(),
-                       sha1( $content->serialize( $content->getDefaultFormat() ) ),
+                       $contentHash,
                        // Account for user name related variables like signatures
-                       $user->getId(),
-                       md5( $user->getName() )
-               ] ) );
-
-               return wfMemcKey( 'prepared-edit', md5( $title->getPrefixedDBkey() ), $hash );
+                       md5( $user->getId() . "\n" . $user->getName() )
+               );
        }
 
        /**
@@ -313,7 +365,7 @@ class ApiStashEdit extends ApiBase {
         *
         * This makes a simple version of WikiPage::prepareContentForEdit() as stash info
         *
-        * @param Content $pstContent
+        * @param Content $pstContent Pre-Save transformed content
         * @param ParserOutput $parserOutput
         * @param string $timestamp TS_MW
         * @param User $user
@@ -355,7 +407,11 @@ class ApiStashEdit extends ApiBase {
                        ],
                        'text' => [
                                ApiBase::PARAM_TYPE => 'text',
-                               ApiBase::PARAM_REQUIRED => true
+                               ApiBase::PARAM_DFLT => null
+                       ],
+                       'stashedtexthash' => [
+                               ApiBase::PARAM_TYPE => 'string',
+                               ApiBase::PARAM_DFLT => null
                        ],
                        'summary' => [
                                ApiBase::PARAM_TYPE => 'string',
index 95659e5..89d9af8 100644 (file)
@@ -64,7 +64,8 @@ class ApiUpload extends ApiBase {
                                $this->dieUsage( 'No upload module set', 'nomodule' );
                        }
                } catch ( UploadStashException $e ) { // XXX: don't spam exception log
-                       $this->handleStashException( $e );
+                       list( $msg, $code ) = $this->handleStashException( get_class( $e ), $e->getMessage() );
+                       $this->dieUsage( $msg, $code );
                }
 
                // First check permission to upload
@@ -112,7 +113,8 @@ class ApiUpload extends ApiBase {
                                $result['imageinfo'] = $this->mUpload->getImageInfo( $this->getResult() );
                        }
                } catch ( UploadStashException $e ) { // XXX: don't spam exception log
-                       $this->handleStashException( $e );
+                       list( $msg, $code ) = $this->handleStashException( get_class( $e ), $e->getMessage() );
+                       $this->dieUsage( $msg, $code );
                }
 
                $this->getResult()->addValue( null, $this->getModuleName(), $result );
@@ -156,20 +158,13 @@ class ApiUpload extends ApiBase {
         */
        private function getStashResult( $warnings ) {
                $result = [];
+               $result['result'] = 'Success';
+               if ( $warnings && count( $warnings ) > 0 ) {
+                       $result['warnings'] = $warnings;
+               }
                // Some uploads can request they be stashed, so as not to publish them immediately.
                // In this case, a failure to stash ought to be fatal
-               try {
-                       $result['result'] = 'Success';
-                       $result['filekey'] = $this->performStash();
-                       $result['sessionkey'] = $result['filekey']; // backwards compatibility
-                       if ( $warnings && count( $warnings ) > 0 ) {
-                               $result['warnings'] = $warnings;
-                       }
-               } catch ( UploadStashException $e ) {
-                       $this->handleStashException( $e );
-               } catch ( Exception $e ) {
-                       $this->dieUsage( $e->getMessage(), 'stashfailed' );
-               }
+               $this->performStash( 'critical', $result );
 
                return $result;
        }
@@ -185,12 +180,7 @@ class ApiUpload extends ApiBase {
                $result['warnings'] = $warnings;
                // in case the warnings can be fixed with some further user action, let's stash this upload
                // and return a key they can use to restart it
-               try {
-                       $result['filekey'] = $this->performStash();
-                       $result['sessionkey'] = $result['filekey']; // backwards compatibility
-               } catch ( Exception $e ) {
-                       $result['warnings']['stashfailed'] = $e->getMessage();
-               }
+               $this->performStash( 'optional', $result );
 
                return $result;
        }
@@ -228,14 +218,7 @@ class ApiUpload extends ApiBase {
                }
 
                if ( $this->mParams['offset'] == 0 ) {
-                       try {
-                               $filekey = $this->performStash();
-                       } catch ( UploadStashException $e ) {
-                               $this->handleStashException( $e );
-                       } catch ( Exception $e ) {
-                               // FIXME: Error handling here is wrong/different from rest of this
-                               $this->dieUsage( $e->getMessage(), 'stashfailed' );
-                       }
+                       $filekey = $this->performStash( 'critical' );
                } else {
                        $filekey = $this->mParams['filekey'];
 
@@ -320,27 +303,57 @@ class ApiUpload extends ApiBase {
        }
 
        /**
-        * Stash the file and return the file key
-        * Also re-raises exceptions with slightly more informative message strings (useful for API)
-        * @throws MWException
-        * @return string File key
+        * Stash the file and add the file key, or error information if it fails, to the data.
+        *
+        * @param string $failureMode What to do on failure to stash:
+        *   - When 'critical', use dieStatus() to produce an error response and throw an exception.
+        *     Use this when stashing the file was the primary purpose of the API request.
+        *   - When 'optional', only add a 'stashfailed' key to the data and return null.
+        *     Use this when some error happened for a non-stash upload and we're stashing the file
+        *     only to save the client the trouble of re-uploading it.
+        * @param array &$data API result to which to add the information
+        * @return string|null File key
         */
-       private function performStash() {
+       private function performStash( $failureMode, &$data = null ) {
                try {
-                       $stashFile = $this->mUpload->stashFile( $this->getUser() );
+                       $status = $this->mUpload->tryStashFile( $this->getUser() );
 
-                       if ( !$stashFile ) {
-                               throw new MWException( 'Invalid stashed file' );
+                       if ( $status->isGood() && !$status->getValue() ) {
+                               // Not actually a 'good' status...
+                               $status->fatal( new ApiRawMessage( 'Invalid stashed file', 'stashfailed' ) );
                        }
-                       $fileKey = $stashFile->getFileKey();
                } catch ( Exception $e ) {
-                       $message = 'Stashing temporary file failed: ' . get_class( $e ) . ' ' . $e->getMessage();
-                       wfDebug( __METHOD__ . ' ' . $message . "\n" );
-                       $className = get_class( $e );
-                       throw new $className( $message );
+                       $debugMessage = 'Stashing temporary file failed: ' . get_class( $e ) . ' ' . $e->getMessage();
+                       wfDebug( __METHOD__ . ' ' . $debugMessage . "\n" );
+                       $status = Status::newFatal( new ApiRawMessage( $e->getMessage(), 'stashfailed' ) );
+               }
+
+               if ( $status->isGood() ) {
+                       $stashFile = $status->getValue();
+                       $data['filekey'] = $stashFile->getFileKey();
+                       // Backwards compatibility
+                       $data['sessionkey'] = $data['filekey'];
+                       return $data['filekey'];
+               }
+
+               if ( $status->getMessage()->getKey() === 'uploadstash-exception' ) {
+                       // The exceptions thrown by upload stash code and pretty silly and UploadBase returns poor
+                       // Statuses for it. Just extract the exception details and parse them ourselves.
+                       list( $exceptionType, $message ) = $status->getMessage()->getParams();
+                       $debugMessage = 'Stashing temporary file failed: ' . $exceptionType . ' ' . $message;
+                       wfDebug( __METHOD__ . ' ' . $debugMessage . "\n" );
+                       list( $msg, $code ) = $this->handleStashException( $exceptionType, $message );
+                       $status = Status::newFatal( new ApiRawMessage( $msg, $code ) );
                }
 
-               return $fileKey;
+               // Bad status
+               if ( $failureMode !== 'optional' ) {
+                       $this->dieStatus( $status );
+               } else {
+                       list( $code, $msg ) = $this->getErrorFromStatus( $status );
+                       $data['stashfailed'] = $msg;
+                       return null;
+               }
        }
 
        /**
@@ -354,12 +367,7 @@ class ApiUpload extends ApiBase {
         * @throws UsageException
         */
        private function dieRecoverableError( $error, $parameter, $data = [], $code = 'unknownerror' ) {
-               try {
-                       $data['filekey'] = $this->performStash();
-                       $data['sessionkey'] = $data['filekey'];
-               } catch ( Exception $e ) {
-                       $data['stashfailed'] = $e->getMessage();
-               }
+               $this->performStash( 'optional', $data );
                $data['invalidparameter'] = $parameter;
 
                $parsed = $this->parseMsg( $error );
@@ -653,49 +661,41 @@ class ApiUpload extends ApiBase {
 
        /**
         * Handles a stash exception, giving a useful error to the user.
-        * @param Exception $e The exception we encountered.
+        * @param string $exceptionType Class name of the exception we encountered.
+        * @param string $message Message of the exception we encountered.
+        * @return array Array of message and code, suitable for passing to dieUsage()
         */
-       protected function handleStashException( $e ) {
-               $exceptionType = get_class( $e );
-
+       protected function handleStashException( $exceptionType, $message ) {
                switch ( $exceptionType ) {
                        case 'UploadStashFileNotFoundException':
-                               $this->dieUsage(
-                                       'Could not find the file in the stash: ' . $e->getMessage(),
+                               return [
+                                       'Could not find the file in the stash: ' . $message,
                                        'stashedfilenotfound'
-                               );
-                               break;
+                               ];
                        case 'UploadStashBadPathException':
-                               $this->dieUsage(
-                                       'File key of improper format or otherwise invalid: ' . $e->getMessage(),
+                               return [
+                                       'File key of improper format or otherwise invalid: ' . $message,
                                        'stashpathinvalid'
-                               );
-                               break;
+                               ];
                        case 'UploadStashFileException':
-                               $this->dieUsage(
-                                       'Could not store upload in the stash: ' . $e->getMessage(),
+                               return [
+                                       'Could not store upload in the stash: ' . $message,
                                        'stashfilestorage'
-                               );
-                               break;
+                               ];
                        case 'UploadStashZeroLengthFileException':
-                               $this->dieUsage(
+                               return [
                                        'File is of zero length, and could not be stored in the stash: ' .
-                                               $e->getMessage(),
+                                               $message,
                                        'stashzerolength'
-                               );
-                               break;
+                               ];
                        case 'UploadStashNotLoggedInException':
-                               $this->dieUsage( 'Not logged in: ' . $e->getMessage(), 'stashnotloggedin' );
-                               break;
+                               return [ 'Not logged in: ' . $message, 'stashnotloggedin' ];
                        case 'UploadStashWrongOwnerException':
-                               $this->dieUsage( 'Wrong owner: ' . $e->getMessage(), 'stashwrongowner' );
-                               break;
+                               return [ 'Wrong owner: ' . $message, 'stashwrongowner' ];
                        case 'UploadStashNoSuchKeyException':
-                               $this->dieUsage( 'No such filekey: ' . $e->getMessage(), 'stashnosuchfilekey' );
-                               break;
+                               return [ 'No such filekey: ' . $message, 'stashnosuchfilekey' ];
                        default:
-                               $this->dieUsage( $exceptionType . ': ' . $e->getMessage(), 'stasherror' );
-                               break;
+                               return [ $exceptionType . ': ' . $message, 'stasherror' ];
                }
        }
 
index 7ab62b5..4678504 100644 (file)
@@ -1,7 +1,8 @@
 {
        "@metadata": {
                "authors": [
-                       "Vodnokon4e"
+                       "Vodnokon4e",
+                       "StanProg"
                ]
        },
        "apihelp-main-param-action": "Кое действие да се извърши.",
@@ -9,6 +10,7 @@
        "apihelp-block-param-user": "Потребителско име, IP адрес или диапазон от IP адреси, които искате да блокирате.",
        "apihelp-block-param-reason": "Причина за блокиране.",
        "apihelp-block-param-nocreate": "Забрана за създаване на потребителски сметки.",
+       "apihelp-block-param-hidename": "Скрива потребителското име от дневника на блокиранията. (Изисква право <code>hideuser</code>)",
        "apihelp-createaccount-description": "Създаване на нова потребителска сметка.",
        "apihelp-createaccount-param-name": "Потребителско име.",
        "apihelp-createaccount-param-email": "Адрес на електронна поща на потребителя (незадължително).",
@@ -25,7 +27,8 @@
        "apihelp-emailuser-param-text": "Съдържание на писмото.",
        "apihelp-emailuser-param-ccme": "Изпращане на копие от това писмо до мен.",
        "apihelp-expandtemplates-param-title": "Заглавие на страница.",
-       "apihelp-feedrecentchanges-param-hideminor": "Скриване на малки редакции.",
+       "apihelp-feedcontributions-param-hideminor": "Скриване на малки промени.",
+       "apihelp-feedrecentchanges-param-hideminor": "Скриване на малки промени.",
        "apihelp-feedrecentchanges-param-hidebots": "Скриване на промени, направени от ботове.",
        "apihelp-feedrecentchanges-param-hideanons": "Скриване на промени, направени от анонимни потребители.",
        "apihelp-feedrecentchanges-param-hideliu": "Скриване на промени, направени от регистрирани потребители.",
@@ -42,5 +45,8 @@
        "apihelp-move-param-movesubpages": "Преименуване на подстраници, ако е приложимо.",
        "apihelp-move-param-noredirect": "Не създавай пренасочване.",
        "apihelp-move-param-ignorewarnings": "Пренебрегване на всякакви предупреждения.",
-       "apihelp-protect-example-protect": "Защита на страница."
+       "apihelp-protect-example-protect": "Защита на страница.",
+       "apihelp-query+langlinks-paramvalue-prop-url": "Добавя пълният URL-адрес.",
+       "apihelp-query+linkshere-paramvalue-prop-title": "Заглавие на всяка страница.",
+       "apihelp-query+watchlist-paramvalue-type-log": "Записи в дневника."
 }
index 8bbef02..e293fed 100644 (file)
        "apihelp-query+watchlist-paramvalue-prop-userid": "Ergänzt die Kennung des Benutzers, der die Bearbeitung ausgeführt hat.",
        "apihelp-query+watchlist-paramvalue-prop-comment": "Ergänzt den Kommentar der Bearbeitung.",
        "apihelp-query+watchlist-paramvalue-prop-timestamp": "Ergänzt den Zeitstempel der Bearbeitung.",
+       "apihelp-query+watchlist-paramvalue-prop-patrol": "Markiert Bearbeitungen, die kontrolliert sind.",
        "apihelp-query+watchlist-paramvalue-prop-sizes": "Ergänzt die alten und neuen Längen der Seite.",
        "apihelp-query+watchlist-paramvalue-type-new": "Seitenerstellungen.",
        "apihelp-query+watchlist-paramvalue-type-log": "Logbucheinträge.",
        "apihelp-query+watchlistraw-param-prop": "Zusätzlich zurückzugebende Eigenschaften:",
+       "apihelp-resetpassword-param-user": "Benutzer, der zurückgesetzt werden soll.",
        "apihelp-rsd-description": "Ein RSD-Schema (Really Simple Discovery) exportieren.",
        "apihelp-rsd-example-simple": "Das RSD-Schema exportieren",
        "apihelp-setnotificationtimestamp-param-entirewatchlist": "An allen beobachteten Seiten arbeiten.",
+       "apihelp-stashedit-param-sectiontitle": "Der Titel für einen neuen Abschnitt.",
        "apihelp-stashedit-param-text": "Seiteninhalt.",
+       "apihelp-stashedit-param-stashedtexthash": "Stattdessen zu verwendende Prüfsumme des Seiteninhalts von einem vorherigen Speicher.",
+       "apihelp-stashedit-param-summary": "Änderungszusammenfassung.",
        "apihelp-tag-param-reason": "Grund für die Änderung.",
+       "apihelp-tokens-param-type": "Abzufragende Tokentypen.",
+       "apihelp-tokens-example-edit": "Ruft einen Bearbeitungstoken ab (Standard).",
+       "apihelp-tokens-example-emailmove": "Ruft einen E-Mail- und Verschiebungstoken ab.",
        "apihelp-unblock-description": "Einen Benutzer freigeben.",
        "apihelp-unblock-param-id": "ID der Sperre zum Entsperren (über <kbd>list=blocks</kbd> erhalten). Darf nicht zusammen mit <var>$1user</var> verwendet werden.",
+       "apihelp-unblock-param-user": "Freizugebender Benutzername, IP-Adressbereich oder freizugebende IP-Adresse. Kann nicht zusammen mit <var>$1id</var> verwendet werden.",
        "apihelp-unblock-param-reason": "Grund für die Freigabe.",
        "apihelp-unblock-param-tags": "Auf den Benutzersperr-Logbuch-Eintrag anzuwendende Änderungsmarkierungen.",
        "apihelp-unblock-example-id": "Sperrkennung #<kbd>105</kbd> freigeben.",
        "api-help-permissions-granted-to": "{{PLURAL:$1|Gewährt an}}: $2",
        "api-help-right-apihighlimits": "Höhere Beschränkungen in API-Anfragen verwenden (langsame Anfragen: $1; schnelle Anfragen: $2). Die Beschränkungen für langsame Anfragen werden auch auf Mehrwertparameter angewandt.",
        "api-help-open-in-apisandbox": "<small>[in Spielwiese öffnen]</small>",
+       "api-help-authmanagerhelper-messageformat": "Zu verwendendes Format zur Rückgabe von Nachrichten.",
        "api-credits-header": "Danksagungen",
        "api-credits": "API-Entwickler:\n* Roan Kattouw (Hauptentwickler von September 2007 bis 2009)\n* Victor Vasiliev\n* Bryan Tong Minh\n* Sam Reed\n* Yuri Astrakhan (Autor, Hauptentwickler von September 2006 bis September 2007)\n* Brad Jorsch (Hauptentwickler seit 2013)\n\nBitte sende deine Kommentare, Vorschläge und Fragen an mediawiki-api@lists.wikimedia.org\noder reiche einen Fehlerbericht auf https://phabricator.wikimedia.org/ ein."
 }
index 7f30ef8..1815836 100644 (file)
 
        "apihelp-login-description": "Log in and get authentication cookies.\n\nThis action should only be used in combination with [[Special:BotPasswords]]; use for main-account login is deprecated and may fail without warning. To safely log in to the main account, use <kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>.",
        "apihelp-login-description-nobotpasswords": "Log in and get authentication cookies.\n\nThis action is deprecated and may fail without warning. To safely log in, use <kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>.",
-       "apihelp-login-description-nonauthmanager": "Log in and get authentication cookies.\n\nIn the event of a successful log-in, the needed cookies will be included in the HTTP response headers. In the event of a failed log-in, further attempts may be throttled to limit automated password guessing attacks.",
        "apihelp-login-param-name": "User name.",
        "apihelp-login-param-password": "Password.",
        "apihelp-login-param-domain": "Domain (optional).",
        "apihelp-stashedit-param-section": "Section number. <kbd>0</kbd> for the top section, <kbd>new</kbd> for a new section.",
        "apihelp-stashedit-param-sectiontitle": "The title for a new section.",
        "apihelp-stashedit-param-text": "Page content.",
+       "apihelp-stashedit-param-stashedtexthash": "Page content hash from a prior stash to use instead.",
        "apihelp-stashedit-param-contentmodel": "Content model of the new content.",
        "apihelp-stashedit-param-contentformat": "Content serialization format used for the input text.",
        "apihelp-stashedit-param-baserevid": "Revision ID of the base revision.",
index ff97cc8..e358bcb 100644 (file)
@@ -6,7 +6,7 @@
                ]
        },
        "apihelp-main-param-format": "La formo de la eligaĵo.",
-       "apihelp-block-description": "Forbari uzulon.",
+       "apihelp-block-description": "Bloki uzanton.",
        "apihelp-block-param-user": "Salutnomo, IP-adreso aŭ IP-adresa intervalo forbarota.",
        "apihelp-block-param-expiry": "Eksvalidiĝa tempo. Ĝi povas esti relativa (ekz. <kbd>5 months</kbd> aŭ <kbd>2 weeks</kbd> aŭ absoluta (ekz. <kbd>2014-09-18T12:34:56Z</kbd>). Se vi indikas <kbd>infinite</kbd> (senfine), <kbd>indefinite</kbd> (nedifinite) aŭ <kbd>never</kbd> (neniam), la forbaro neniam eksvalidiĝos.",
        "apihelp-createaccount-param-name": "Uzantnomo.",
        "apihelp-feedrecentchanges-param-hideanons": "Kaŝi redaktojn de anonimuloj.",
        "apihelp-feedrecentchanges-param-hideliu": "Kaŝi redaktojn de ensalutintaj uzantoj.",
        "apihelp-feedrecentchanges-param-hidepatrolled": "Kaŝi reviziitajn ŝanĝojn.",
-       "apihelp-feedrecentchanges-param-hidemyself": "Kaŝi redaktojn de la nun ensalutinta uzulo (= vi).",
+       "apihelp-feedrecentchanges-param-hidemyself": "Kaŝi ŝanĝojn faritajn de la nuna uzanto.",
        "apihelp-feedrecentchanges-param-hidecategorization": "Kaŝi ŝanĝojn de kategoria aneco.",
        "apihelp-feedrecentchanges-example-simple": "Montri ĵusajn ŝanĝojn.",
        "apihelp-filerevert-description": "Restarigi malnovan version de dosiero.",
        "apihelp-filerevert-param-comment": "Alŝuta komento.",
        "apihelp-login-param-name": "Uzantnomo.",
        "apihelp-login-param-password": "Pasvorto.",
-       "apihelp-login-example-login": "Ensaluti."
+       "apihelp-login-example-login": "Ensaluti.",
+       "apihelp-userrights-param-user": "Uzantnomo."
 }
index 0d6d46c..80eec50 100644 (file)
@@ -34,7 +34,7 @@
        "apihelp-main-param-maxlag": "La latence maximale peut être utilisée quand MédiaWiki est installé sur un cluster de base de données répliqué. Pour éviter des actions provoquant un supplément de latence de réplication de site, ce paramètre peut faire attendre le client jusqu’à ce que la latence de réplication soit inférieure à une valeur spécifiée. En cas de latence excessive, le code d’erreur <samp>maxlag</samp> est renvoyé avec un message tel que <samp>Attente de $host : $lag secondes de délai</samp>.<br />Voyez [[mw:Manual:Maxlag_parameter|Manuel: Maxlag parameter]] pour plus d’information.",
        "apihelp-main-param-smaxage": "Fixer l’entête HTTP de contrôle de cache <code>s-maxage</code> à ce nombre de secondes. Les erreurs ne sont jamais mises en cache.",
        "apihelp-main-param-maxage": "Fixer l’entête HTTP de contrôle de cache <code>max-age</code> à ce nombre de secondes. Les erreurs ne sont jamais mises en cache.",
-       "apihelp-main-param-assert": "Vérifier si l’utilisateur est connecté si positionné à <kbd>user</kbd>, ou a le droit utilisateur robot si positionné à <kbd>bot</kbd>.",
+       "apihelp-main-param-assert": "Vérifier si l’utilisateur est connecté si positionné à <kbd>user</kbd>, ou s'il a le droit d'un utilisateur robot si positionné à <kbd>bot</kbd>.",
        "apihelp-main-param-requestid": "Toute valeur fournie ici sera incluse dans la réponse. Peut être utilisé pour distinguer des demandes.",
        "apihelp-main-param-servedby": "Inclure le nom d’hôte qui a renvoyé la requête dans les résultats.",
        "apihelp-main-param-curtimestamp": "Inclure l’horodatage actuel dans le résultat.",
        "apihelp-linkaccount-example-link": "Commencer le processus de liaison d’un compte depuis <kbd>Exemple</kbd>.",
        "apihelp-login-description": "Se connecter et obtenir les cookies d’authentification.\n\nCette action ne devrait être utilisée qu’en lien avec [[Special:BotPasswords]] ; l’utiliser pour la connexion du compte principal est obsolète et peut échouer sans avertissement. Pour se connecter sans problème au compte principal, utiliser <kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>.",
        "apihelp-login-description-nobotpasswords": "Se connecter et obtenir les cookies d’authentification.\n\nCette action est obsolète et peut échouer sans prévenir. Pour se connecter sans problème, utiliser <kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>.",
-       "apihelp-login-description-nonauthmanager": "Se connecter et obtenir les cookies d’authentification.\n\nDans le cas d’une connexion réussie, les cookies nécessaires seront inclus dans les entêtes HTTP de la réponse. Dans le cas d’une connexion en échec, des tentatives ultérieures pourront être limitées pour éviter les attaques automatiques pour deviner les mots de passe.",
        "apihelp-login-param-name": "Nom d’utilisateur.",
        "apihelp-login-param-password": "Mot de passe.",
        "apihelp-login-param-domain": "Domaine (facultatif).",
        "apihelp-stashedit-param-section": "Numéro de section. <kbd>0</kbd> pour la section du haut, <kbd>new</kbd> pour une nouvelle section.",
        "apihelp-stashedit-param-sectiontitle": "Le titre pour une nouvelle section.",
        "apihelp-stashedit-param-text": "Contenu de la page.",
+       "apihelp-stashedit-param-stashedtexthash": "A substituer par le hachage du contenu de la page venant d’une réserve antérieure.",
        "apihelp-stashedit-param-contentmodel": "Modèle de contenu du nouveau contenu.",
        "apihelp-stashedit-param-contentformat": "Format de sérialisation de contenu utilisé pour le texte saisi.",
        "apihelp-stashedit-param-baserevid": "ID de révision de la révision de base.",
index c5aef1d..b752751 100644 (file)
@@ -23,7 +23,7 @@
        "apihelp-main-param-requestid": "Calquera valor dado aquí será incluído na resposta. Pode usarse para distingir peticións.",
        "apihelp-main-param-servedby": "Inclúa o nome do servidor que servía a solicitude nos resultados.",
        "apihelp-main-param-curtimestamp": "Incluir a marca de tempo actual no resultado.",
-       "apihelp-main-param-origin": "Cando se accede á API usando unha petición AJAX entre-dominios (CORS), inicializar o parámetro co dominio orixe. Isto debe incluírse en calquera petición pre-flight, e polo tanto debe ser parte da petición URI (non do corpo POST). Debe coincidir exactamente cunha das orixes na cabeceira <code>Origin</code>, polo que ten que ser fixado a algo como <kbd>https://en.wikipedia.org</kbd> ou <kbd>https://meta.wikimedia.org</kbd>. Se este parámetro non coincide coa cabeceira <code>Origin</code>, devolverase unha resposta 403. Se este parámetro coincide coa cabeceira <code>Origin</code> e a orixe está na lista branca, porase unha cabeceira <code>Access-Control-Allow-Origin</code>.",
+       "apihelp-main-param-origin": "Cando se accede á API usando unha petición AJAX entre-dominios (CORS), inicializar o parámetro co dominio orixe. Isto debe incluírse en calquera petición pre-flight, e polo tanto debe ser parte da petición URI (non do corpo POST). Para peticións autenticadas, isto debe coincidir exactamente cunha das orixes na cabeceira <code>Origin</code>, polo que ten que ser fixado a algo como <kbd>https://en.wikipedia.org</kbd> ou <kbd>https://meta.wikimedia.org</kbd>. Se este parámetro non coincide coa cabeceira <code>Origin</code>, devolverase unha resposta 403. Se este parámetro coincide coa cabeceira <code>Origin</code> e a orixe está na lista branca, as cabeceiras <code>Access-Control-Allow-Origin</code> e <code>Access-Control-Allow-Credentials</code> serán fixadas.\n\nPara peticións non autenticadas, especifique o valor <kbd>*</kbd>. Isto fará que se fixe a cabeceira <code>Access-Control-Allow-Origin</code>, pero <code>Access-Control-Allow-Credentials</code> será <code>false</code> e todos os datos específicos do usuario serán ocultados.",
        "apihelp-main-param-uselang": "Linga a usar para a tradución de mensaxes. <kbd>[[Special:ApiHelp/query+siteinfo|action=query&meta=siteinfo]]</kbd> con <kbd>siprop=languages</kbd> devolve unha lista de códigos de lingua, ou especificando <kbd>user</kbd> coa preferencia de lingua do usuario actual, ou especificando <kbd>content</kbd> para usar a lingua do contido desta wiki.",
        "apihelp-block-description": "Bloquear un usuario.",
        "apihelp-block-param-user": "Nome de usuario, dirección ou rango de IPs que quere bloquear.",
@@ -60,6 +60,7 @@
        "apihelp-compare-param-torev": "Segunda revisión a comparar.",
        "apihelp-compare-example-1": "Mostrar diferencias entre a revisión 1 e a 2",
        "apihelp-createaccount-description": "Crear unha nova conta de usuario.",
+       "apihelp-createaccount-param-preservestate": "SE <kbd>[[Special:ApiHelp/query+authmanagerinfo|action=query&meta=authmanagerinfo]]</kbd> devolve o valor \"certo\" para  <samp>hasprimarypreservedstate</samp>, as consultas marcadas como <samp>primary-required</samp> deben ser omitidas. Se devolve un valor non baleiro para <samp>preservedusername</samp>, ese nome de usuario debe usarse para o parámetro <var>username</var>.",
        "apihelp-createaccount-example-create": "Comezar o proceso de crear un usuario <kbd>Exemplo</kbd> con contrasinal <kbd>ExemploContrasinal</kbd>.",
        "apihelp-createaccount-param-name": "Nome de usuario.",
        "apihelp-createaccount-param-password": "Contrasinal (ignorado se <var>$1mailpassword</var> está activo)",
        "apihelp-import-example-import": "Importar [[meta:Help:ParserFunctions]] ó espazo de nomes 100 con todo o historial.",
        "apihelp-linkaccount-description": "Vincular unha conta dun provedor externo ó usuario actual.",
        "apihelp-linkaccount-example-link": "Comezar o proceso de vincular a unha conta de <kbd>Exemplo</kbd>.",
-       "apihelp-login-description": "No caso dunha conexión correcta, as cookies necesarias incluiranse nas cabeceiras HTTP de resposta. No caso dunha conexión fallida, os intentos posteriores poden ser reducidos para limitar ataques automaticos de roubo de contrasinais.",
+       "apihelp-login-description": "Iniciar sesión e obter as cookies de autenticación.\n\nEsta acción só debe utilizarse en combinación con [[Special:BotPasswords]]; para a cuenta de inicio de sesión non se utiliza e pode fallar sen previo aviso. Para iniciar a sesión de forma segura na conta principal, utilice <kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>.",
        "apihelp-login-description-nobotpasswords": "Conectarse e obter as cookies de autenticación. \n\nEsta acción está obsoleta e pode fallar sen avisar. Para conectarse sen problema use <kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>.",
-       "apihelp-login-description-nonauthmanager": "Conectarse e obter as cookies de autenticación. \n\nNo caso dunha conexión correcta, as cookies necesarias incluiranse nas cabeceiras HTTP de resposta. No caso dunha conexión fallida, os intentos posteriores poden ser reducidos para limitar ataques automaticos de roubo de contrasinais.",
        "apihelp-login-param-name": "Nome de usuario.",
        "apihelp-login-param-password": "Contrasinal",
        "apihelp-login-param-domain": "Dominio (opcional).",
        "apihelp-stashedit-param-section": "Número de selección. O <kbd>0</kbd> é para a sección superior, <kbd>novo</kbd> para unha sección nova.",
        "apihelp-stashedit-param-sectiontitle": "Título para unha nova sección.",
        "apihelp-stashedit-param-text": "Contido da páxina.",
+       "apihelp-stashedit-param-stashedtexthash": "Función hash do contido da páxina dunha reserva anterior para ser usada.",
        "apihelp-stashedit-param-contentmodel": "Modelo de contido para o novo contido.",
        "apihelp-stashedit-param-contentformat": "Formato de serialización de contido utilizado para o texto de entrada.",
        "apihelp-stashedit-param-baserevid": "Identificador da revisión da revisión de base.",
        "api-help-permissions-granted-to": "{{PLURAL:$1|Concedida a|Concedidas a}}: $2",
        "api-help-right-apihighlimits": "Usar os valores superiores das consultas da API (consultas lentas: $1; consultas rápidas: $2). Os límites para as consultas lentas tamén se aplican ós parámetros multivaluados.",
        "api-help-open-in-apisandbox": "<small>[abrir en zona de probas]</small>",
+       "api-help-authmanager-general-usage": "O procedemento xeral para usar este módulo é:\n# Buscar os campos dispoñibles dende <kbd>[[Special:ApiHelp/query+authmanagerinfo|\n\naction=query&meta=authmanagerinfo]]</kbd> con <kbd>amirequestsfor=$4</kbd>, e un identificador <kbd>$5</kbd> de <kbd>[[Special:ApiHelp/query+tokens|action=query&meta=tokens]]</kbd>.\n# Presentar os campos ó usuario, e obter o seu envío.\n# Enviar a este módulo, proporcionando <var>$1returnurl</var> e calquera campo relevante.\n# Comprobar o <samp>status</samp> na resposta.\n#* Se vostede recibe <samp>PASS</samp> ou <samp>FAIL</samp>, a acción rematou. A operación foi correcta ou non se fixo.\n#* Se vostede recibe <samp>UI</samp>, presenta os novos campos ó usuario e obtén o seu envío. Logo son enviados a este módulo con <var>$1continue</var> e o conxunto de campos relevantes, e repite o paso 4.\n#* Se vostede recibe <samp>REDIRECT</samp>, dirixe ó usuario a <samp>redirecttarget</samp> e espera pola resposta a <var>$1returnurl</var>. Logo envíaa a este módulo con <var>$1continue</var> e calquera campo pasado á URL de volta, e repite o paso 4.\n#* Se recibe <samp>RESTART</samp>, isto significa que a autenticación funcionou pero que non temos unha conta de usuario ligada. Debe tratar isto igual que <samp>UI</samp> ou como <samp>FAIL</samp>.",
        "api-help-authmanagerhelper-requests": "Só usar estas peticións de autenticación, co <samp>id</samp> devolto por <kbd>[[Special:ApiHelp/query+authmanagerinfo|action=query&meta=authmanagerinfo]]</kbd> con <kbd>amirequestsfor=$1</kbd> ou dunha resposta previa deste módulo.",
        "api-help-authmanagerhelper-request": "Usar esta petición de autenticación, co <samp>id</samp> devolto por <kbd>[[Special:ApiHelp/query+authmanagerinfo|action=query&meta=authmanagerinfo]]</kbd> con <kbd>amirequestsfor=$1</kbd>.",
        "api-help-authmanagerhelper-messageformat": "Formato a usar para devolver as mensaxes.",
        "api-help-authmanagerhelper-mergerequestfields": "Fusionar os campos de información para todas as peticións de autenticación nunha táboa.",
        "api-help-authmanagerhelper-preservestate": "Conservar o estado dun intento previo de conexión fallida, se é posible.",
+       "api-help-authmanagerhelper-returnurl": "Devolve o URL para os fluxos de autenticación de terceiros, que debe ser absoluto. Este ou <var>$1continue</var> é obrigatorio.\n\nLogo da recepción dunha resposta <samp>REDIRECT</samp>, vostede normalmente abrirá un navegador web ou un visor web para ver a URL <samp>redirecttarget</samp> especificada para un fluxo de autenticación de terceiros. Cando isto se complete, a aplicación de terceiros enviará ó navegador web ou visor web a esta URL. Vostede debe eliminar calquera consulta ou parámetros POST da URL e pasalos como unha consulta <var>$1continue</var> a este módulo API.",
        "api-help-authmanagerhelper-continue": "Esta petición é unha continucación despois dun resposta precedente <samp>UI</samp> ou <samp>REDIRECT</samp>. Esta ou <var>$1returnurl</var> é requirida.",
+       "api-help-authmanagerhelper-additional-params": "Este módulo acepta parámetros adicionais dependendo das consultas de autenticación dispoñibles. Use <kbd>[[Special:ApiHelp/query+authmanagerinfo|action=query&meta=authmanagerinfo]]</kbd> con <kbd>amirequestsfor=$1</kbd> (ou unha resposta previa deste módulo, se aplicable) para determinar as consultas dispoñibles e os campos que usan.",
        "api-credits-header": "Créditos",
        "api-credits": "Desenvolvedores da API:\n* Roan Kattouw (desenvolvedor principal, set. 2007-2009)\n* Victor Vasiliev\n* Bryan Tong Minh\n* Sam Reed\n* Yuri Astrakhan (creador e desenvolvedor principal, set. 2006-sep. 2007)\n* Brad Jorsch (desenvolvedor principal, 2013-actualidade)\n\nEnvía comentarios, suxerencias e preguntas a mediawiki-api@lists.wikimedia.org\nou informa dun erro en https://phabricator.wikimedia.org/."
 }
index 08a27d6..a28cbda 100644 (file)
        "apihelp-linkaccount-example-link": "תחילת תהליך הקישור לחשבון מ־<kbd>Example</kbd>.",
        "apihelp-login-description": "להיכנס ולקבל עוגיות אימות.\n\nהפעולה הזאת צריכה לשמש רק בשילוב [[Special:BotPasswords]]; שימוש לכניסה לחשבון ראשי מיושן ועשוי להיכשל ללא אזהרה. כדי להיכנס בבטחה לחשבון הראשי, יש להשתמש ב־<kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>.",
        "apihelp-login-description-nobotpasswords": "להיכנס ולקבל עוגיות אימות.\n\nהפעולה הזאת מיושנת ועשויה להיכשל ללא אזהרה. כדי להיכנס בבטחה, יש להשתמש ב־<kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>.",
-       "apihelp-login-description-nonauthmanager": "להיכנס ולקבל עוגיות אימות.\n\nבמקרה של כניסה מוצלחת, העוגיות המקוננות תיכללנה בכותרות תשובות ה־HTTP. במקרה של כניסה כושלת, הניסיונות הבאים יוגבלו למספר ניסויי ניחוש הססמה האוטומטיים.",
        "apihelp-login-param-name": "שם משתמש.",
        "apihelp-login-param-password": "ססמה.",
        "apihelp-login-param-domain": "שם מתחם (רשות).",
        "apihelp-stashedit-param-section": "מספר הפסקה. <kbd>0</kbd> עבור הפסקה הראשונה, <kbd>new</kbd> עבור פסקה חדשה.",
        "apihelp-stashedit-param-sectiontitle": "כותרת הפסקה החדשה.",
        "apihelp-stashedit-param-text": "תוכן הדף.",
+       "apihelp-stashedit-param-stashedtexthash": "גיבוב של תוכן דף מסליק קודם שישמש במקום זה.",
        "apihelp-stashedit-param-contentmodel": "מודל התוכן של התוכן החדש.",
        "apihelp-stashedit-param-contentformat": "תסדיר הסדרת תוכן עבור טקסט הקלט.",
        "apihelp-stashedit-param-baserevid": "מזהה גסה של גרסת הבסיס.",
index 6c47aa4..650acb9 100644 (file)
        "apihelp-linkaccount-example-link": "{{doc-apihelp-example|linkaccount}}",
        "apihelp-login-description": "{{doc-apihelp-description|login|info=This message is used when <code>$wgEnableBotPasswords</code> is true.|seealso=* {{msg-mw|apihelp-login-description-nobotpasswords}}}}",
        "apihelp-login-description-nobotpasswords": "{{doc-apihelp-description|login|info=This message is used when <code>$wgEnableBotPasswords</code> is false.|seealso=* {{msg-mw|apihelp-login-description}}}}",
-       "apihelp-login-description-nonauthmanager": "{{doc-apihelp-description|login|info=This message is used when <code>$wgDisableAuthManager</code> is true.|seealso=* {{msg-mw|apihelp-login-description}}}}",
        "apihelp-login-param-name": "{{doc-apihelp-param|login|name}}\n{{Identical|Username}}",
        "apihelp-login-param-password": "{{doc-apihelp-param|login|password}}\n{{Identical|Password}}",
        "apihelp-login-param-domain": "{{doc-apihelp-param|login|domain}}",
        "apihelp-stashedit-param-section": "{{doc-apihelp-param|stashedit|section}}",
        "apihelp-stashedit-param-sectiontitle": "{{doc-apihelp-param|stashedit|sectiontitle}}",
        "apihelp-stashedit-param-text": "{{doc-apihelp-param|stashedit|text}}",
+       "apihelp-stashedit-param-stashedtexthash": "{{doc-apihelp-param|stashedit|stashedtexthash}}",
        "apihelp-stashedit-param-contentmodel": "{{doc-apihelp-param|stashedit|contentmodel}}",
        "apihelp-stashedit-param-contentformat": "{{doc-apihelp-param|stashedit|contentformat}}",
        "apihelp-stashedit-param-baserevid": "{{doc-apihelp-param|stashedit|baserevid}}",
index 9e5d754..45b43df 100644 (file)
        "apihelp-linkaccount-example-link": "Почати процес пов'язування з обліковм записом з <kbd>Example</kbd>.",
        "apihelp-login-description": "Увійти в систему й отримати куки автентифікації.\n\nЦю дію треба використовувати лише в комбінації з [[Special:BotPasswords]]; використання для входу в основний обліковий запис застаріле і може ламатися без попередження. Щоб безпечно увійти в основний обліковий запис, використовуйте <kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>.",
        "apihelp-login-description-nobotpasswords": "Увійти й отримати куки автентифікації.\n\nЦя дія застаріла і може ламатися без попередження. Щоб безпечно входити в систему, використовуйте <kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>.",
-       "apihelp-login-description-nonauthmanager": "Увійти й отримати куки автентифікації.\n\nУ випадку успішного входження в систему будуть включені в заголовки відповіді HTTP. У випадку невдалого входження подальші спроби можуть бути урізані, щоб обмежити атаки автоматичного вгадування пароля.",
        "apihelp-login-param-name": "Ім'я користувача.",
        "apihelp-login-param-password": "Пароль.",
        "apihelp-login-param-domain": "Домен (необов'язково).",
        "apihelp-stashedit-param-section": "Номер розділу. <kbd>0</kbd> для вступного розділу, <kbd>new</kbd> для нового розділу.",
        "apihelp-stashedit-param-sectiontitle": "Назва нового розділу.",
        "apihelp-stashedit-param-text": "Вміст сторінки.",
+       "apihelp-stashedit-param-stashedtexthash": "Хеш вмісту сторінки з попереднього сховку, який треба використати натомість.",
        "apihelp-stashedit-param-contentmodel": "Модель вмісту нового вмісту.",
        "apihelp-stashedit-param-contentformat": "Формат серіалізації вмісту, використовуваний для введеного тексту.",
        "apihelp-stashedit-param-baserevid": "Ідентифікатор базової версії.",
index 448233c..037aff4 100644 (file)
@@ -34,7 +34,7 @@
        "apihelp-main-param-requestid": "任何在此提供的值将包含在响应中。可能可以用以区别请求。",
        "apihelp-main-param-servedby": "包含保存结果请求的主机名。",
        "apihelp-main-param-curtimestamp": "在结果中包括当前时间戳。",
-       "apihelp-main-param-origin": "当通过跨域名AJAX请求(CORS)访问API时,设置此作为起始域名。这必须包括在任何pre-flight请求中,并因此必须是请求的URI的一部分(而不是POST正文)。\n\n对于已验证的请求,这必须正确匹配<code>Origin</code>标头中的原点之一,因此它已经设置为像<kbd>https://zh.wikipedia.org</kbd>或<kbd>https://meta.wikimedia.org</kbd>的东西。如果此参数不匹配<code>Origin</code>页顶,就返回403错误响应。如果此参数匹配<code>Origin</code>页顶并且起点在白名单中,将设置<code>Access-Control-Allow-Origin</code>和<code>Access-Control-Allow-Credentials</code>开头。\n\n对于未验证的请求,会指定值<kbd>*</kbd>。这将导致<code>Access-Control-Allow-Origin</code>标头被设置,但<code>Access-Control-Allow-Credentials</code>将为<code>false</code>,且所有用户特定数据将受限制。",
+       "apihelp-main-param-origin": "当通过跨域名AJAX请求(CORS)访问API时,设置此作为起始域名。这必须包括在任何pre-flight请求中,并因此必须是请求的URI的一部分(而不是POST正文)。\n\n对于已验证的请求,这必须正确匹配<code>Origin</code>标头中的原点之一,因此它已经设置为像<kbd>https://zh.wikipedia.org</kbd>或<kbd>https://meta.wikimedia.org</kbd>的东西。如果此参数不匹配<code>Origin</code>页顶,就返回403错误响应。如果此参数匹配<code>Origin</code>页顶并且起点被白名单,将设置<code>Access-Control-Allow-Origin</code>和<code>Access-Control-Allow-Credentials</code>开头。\n\n对于未验证的请求,会指定值<kbd>*</kbd>。这将导致<code>Access-Control-Allow-Origin</code>标头被设置,但<code>Access-Control-Allow-Credentials</code>将为<code>false</code>,且所有用户特定数据将受限制。",
        "apihelp-main-param-uselang": "用于消息翻译的语言。<kbd>[[Special:ApiHelp/query+siteinfo|action=query&meta=siteinfo]]</kbd>与<kbd>siprop=languages</kbd>可返回语言代码列表,或指定<kbd>user</kbd>以使用当前用户的语言设置,或指定<kbd>content</kbd>以使用此wiki的内容语言。",
        "apihelp-block-description": "封禁一位用户。",
        "apihelp-block-param-user": "您要封禁的用户、IP地址或IP地址段。",
@@ -86,6 +86,7 @@
        "apihelp-createaccount-example-mail": "创建用户<kbd>testmailuser</kbd>并电邮发送一个随机生成的密码。",
        "apihelp-cspreport-description": "由浏览器使用以报告违反内容安全方针的内容。此模块应永不使用,除了在被CSP兼容的浏览器自动使用时。",
        "apihelp-cspreport-param-reportonly": "标记作为来自监视方针的报告,而不是执行方针的报告",
+       "apihelp-cspreport-param-source": "生成引发此报告的CSP标头的事物",
        "apihelp-delete-description": "删除一个页面。",
        "apihelp-delete-param-title": "要删除的页面标题。不能与<var>$1pageid</var>一起使用。",
        "apihelp-delete-param-pageid": "要删除的页面的页面 ID。不能与<var>$1title</var>一起使用。",
        "apihelp-linkaccount-example-link": "开始从<kbd>Example</kbd>链接至账户的过程。",
        "apihelp-login-description": "登录并获取身份验证Cookie。\n\n此操作只应与[[Special:BotPasswords]]一起使用;用于主账户登录的方式已弃用,并可能在没有警告的情况下失败。要安全登录主账户,请使用<kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>。",
        "apihelp-login-description-nobotpasswords": "登录并获取身份验证Cookie。\n\n此操作已弃用,并可能在没有警告的情况下失败。要安全登录,请使用<kbd>[[Special:ApiHelp/clientlogin|action=clientlogin]]</kbd>。",
-       "apihelp-login-description-nonauthmanager": "登录并获取身份验证Cookie。\n\n在成功登录的情况下,所需的Cookie将包含在HTTP响应头中。在登录失败的情况下,进一步的尝试可能会被自动密码猜解攻击的限制所遏制。",
        "apihelp-login-param-name": "用户名。",
        "apihelp-login-param-password": "密码。",
        "apihelp-login-param-domain": "域名(可选)。",
        "apihelp-query+random-param-filterredir": "如何过滤重定向。",
        "apihelp-query+random-example-simple": "从主名字空间返回两个随机页面。",
        "apihelp-query+random-example-generator": "返回有关来自主名字空间的两个随机页面的页面信息。",
-       "apihelp-query+recentchanges-description": "举最近更改。",
+       "apihelp-query+recentchanges-description": "举最近更改。",
        "apihelp-query+recentchanges-param-start": "枚举的起始时间戳。",
        "apihelp-query+recentchanges-param-end": "枚举的结束时间戳。",
        "apihelp-query+recentchanges-param-namespace": "过滤更改为仅限这些名字空间。",
        "apihelp-query+recentchanges-paramvalue-prop-ids": "添加页面ID、最近更改ID和新旧修订的ID。",
        "apihelp-query+recentchanges-paramvalue-prop-sizes": "添加新旧页面长度(字节)。",
        "apihelp-query+recentchanges-paramvalue-prop-redirect": "如果页面是重定向的话,标记编辑。",
-       "apihelp-query+recentchanges-paramvalue-prop-patrolled": "Tags patrollable edits as being patrolled or unpatrolled.",
+       "apihelp-query+recentchanges-paramvalue-prop-patrolled": "将可巡查编辑标记为已巡查或未巡查。",
        "apihelp-query+recentchanges-paramvalue-prop-loginfo": "添加日志信息(日志ID、日志类型等)至日志记录。",
        "apihelp-query+recentchanges-paramvalue-prop-tags": "列举条目的标签。",
        "apihelp-query+recentchanges-paramvalue-prop-sha1": "Adds the content checksum for entries associated with a revision.",
        "apihelp-stashedit-param-section": "段落数。<kbd>0</kbd>用于首段,<kbd>new</kbd>用于新的段落。",
        "apihelp-stashedit-param-sectiontitle": "新段落的标题。",
        "apihelp-stashedit-param-text": "页面内容。",
+       "apihelp-stashedit-param-stashedtexthash": "要使用的来自先前暂存处的页面内容哈希。",
        "apihelp-stashedit-param-contentmodel": "新内容的内容模型。",
        "apihelp-stashedit-param-contentformat": "用于输入文本的内容序列化格式。",
        "apihelp-stashedit-param-baserevid": "基础修订的修订ID。",
index 82eeff0..eab5068 100644 (file)
@@ -105,12 +105,6 @@ class AuthManager implements LoggerAwareInterface {
         * @return AuthManager
         */
        public static function singleton() {
-               global $wgDisableAuthManager;
-
-               if ( $wgDisableAuthManager ) {
-                       throw new \BadMethodCallException( '$wgDisableAuthManager is set' );
-               }
-
                if ( self::$instance === null ) {
                        self::$instance = new self(
                                \RequestContext::getMain()->getRequest(),
index 361fe23..8c2a19e 100644 (file)
@@ -48,7 +48,7 @@ class BacklinkCache {
         *  > (string) links table name
         *   > (int) batch size
         *    > 'numRows' : Number of rows for this link table
-        *    > 'batches' : array( $start, $end )
+        *    > 'batches' : [ $start, $end ]
         *
         * @see BacklinkCache::partitionResult()
         *
index f5d3c33..530fc76 100644 (file)
@@ -150,7 +150,7 @@ class IcuCollation extends Collation {
                'la' => [],
                'lb' => [],
                'lt' => [ "Č", "Š", "Ž" ],
-               'mk' => [],
+               'mk' => [ "Ѓ", "Ќ" ],
                'mo' => [ "Ă", "Â", "Î", "Ş", "Ţ" ],
                'mt' => [ "Ċ", "Ġ", "Għ", "Ħ", "Ż" ],
                'nl' => [],
index 845e39c..9c11035 100644 (file)
@@ -37,7 +37,7 @@ class CssContentHandler extends CodeContentHandler {
        }
 
        protected function getContentClass() {
-               return 'CssContent';
+               return CssContent::class;
        }
 
        public function supportsRedirects() {
index b082b32..9abad3e 100644 (file)
@@ -39,7 +39,7 @@ class JavaScriptContentHandler extends CodeContentHandler {
         * @return string
         */
        protected function getContentClass() {
-               return 'JavaScriptContent';
+               return JavaScriptContent::class;
        }
 
        public function supportsRedirects() {
index f97eaa4..eb1c67d 100644 (file)
@@ -37,6 +37,6 @@ class JsonContentHandler extends CodeContentHandler {
         * @return string
         */
        protected function getContentClass() {
-               return 'JsonContent';
+               return JsonContent::class;
        }
 }
index d4fad44..74cbd16 100644 (file)
@@ -101,7 +101,7 @@ class TextContentHandler extends ContentHandler {
         * @return string
         */
        protected function getContentClass() {
-               return 'TextContent';
+               return TextContent::class;
        }
 
        /**
index 5c0a9c8..d9f1e86 100644 (file)
@@ -35,7 +35,7 @@ class WikitextContentHandler extends TextContentHandler {
        }
 
        protected function getContentClass() {
-               return 'WikitextContent';
+               return WikitextContent::class;
        }
 
        /**
index 3690735..c24962b 100644 (file)
  *   - READ_EXCLUSIVE : Up-to-date read as of now, that locks (exclusive) the records
  * All record locks persist for the duration of the transaction.
  *
+ * A special constant READ_LATEST_IMMUTABLE can be used for fetching append-only data. Such
+ * data is either (a) on a slave and up-to-date or (b) not yet there, but on the master/quorum.
+ * Because the data is append-only, it can never be stale on a slave if present.
+ *
  * Callers should use READ_NORMAL (or pass in no flags) unless the read determines a write.
  * In theory, such cases may require READ_LOCKING, though to avoid contention, READ_LATEST is
  * often good enough. If UPDATE race condition checks are required on a row and expensive code
  * must run after the row is fetched to determine the UPDATE, it may help to do something like:
- *   - a) Read the current row
- *   - b) Determine the new row (expensive, so we don't want to hold locks now)
- *   - c) Re-read the current row with READ_LOCKING; if it changed then bail out
- *   - d) otherwise, do the updates
+ *   - a) Start transaction
+ *   - b) Read the current row with READ_LATEST
+ *   - c) Determine the new row (expensive, so we don't want to hold locks now)
+ *   - d) Re-read the current row with READ_LOCKING; if it changed then bail out
+ *   - e) otherwise, do the updates
+ *   - f) Commit transaction
  *
  * @since 1.20
  */
 interface IDBAccessObject {
-       // Constants for object loading bitfield flags (higher => higher QoS)
-       const READ_LATEST = 1; // read from the master
+       /** Constants for object loading bitfield flags (higher => higher QoS) */
+       /** @var integer Read from a slave/non-quorum */
+       const READ_NORMAL = 0;
+       /** @var integer Read from the master/quorum */
+       const READ_LATEST = 1;
+       /* @var integer Read from the master/quorum and lock out other writers */
        const READ_LOCKING = 3; // READ_LATEST (1) and "LOCK IN SHARE MODE" (2)
+       /** @var integer Read from the master/quorum and lock out other writers and locking readers */
        const READ_EXCLUSIVE = 7; // READ_LOCKING (3) and "FOR UPDATE" (4)
 
-       // Convenience constant for callers to explicitly request slave data
-       const READ_NORMAL = 0; // read from the slave
+       /** @var integer Read from a slave/non-quorum immutable data, using the master/quorum on miss */
+       const READ_LATEST_IMMUTABLE = 8;
 
        // Convenience constant for tracking how data was loaded (higher => higher QoS)
        const READ_NONE = -1; // not loaded yet (or the object was cleared)
index 3dc6e92..5023acd 100644 (file)
@@ -783,6 +783,7 @@ abstract class DatabaseBase implements IDatabase {
        public function query( $sql, $fname = __METHOD__, $tempIgnore = false ) {
                global $wgUser;
 
+               $priorWritesPending = $this->writesOrCallbacksPending();
                $this->mLastQuery = $sql;
 
                $isWriteQuery = $this->isWriteQuery( $sql );
@@ -810,7 +811,10 @@ abstract class DatabaseBase implements IDatabase {
                // Or, for one-word queries (like "BEGIN" or COMMIT") add it to the end (bug 42598)
                $commentedSql = preg_replace( '/\s|$/', " /* $fname $userName */ ", $sql, 1 );
 
-               if ( !$this->mTrxLevel && $this->getFlag( DBO_TRX ) && $this->isTransactableQuery( $sql ) ) {
+               # Start implicit transactions that wrap the request if DBO_TRX is enabled
+               if ( !$this->mTrxLevel && $this->getFlag( DBO_TRX )
+                       && $this->isTransactableQuery( $sql )
+               ) {
                        $this->begin( __METHOD__ . " ($fname)" );
                        $this->mTrxAutomatic = true;
                }
@@ -862,31 +866,23 @@ abstract class DatabaseBase implements IDatabase {
 
                # Try reconnecting if the connection was lost
                if ( false === $ret && $this->wasErrorReissuable() ) {
-                       # Transaction is gone; this can mean lost writes or REPEATABLE-READ snapshots
-                       $hadTrx = $this->mTrxLevel;
-                       # T127428: for non-write transactions, a disconnect and a COMMIT are similar:
-                       # neither changed data and in both cases any read snapshots are reset anyway.
-                       $isNoopCommit = ( !$this->writesOrCallbacksPending() && $sql === 'COMMIT' );
-                       # Update state tracking to reflect transaction loss
-                       $this->mTrxLevel = 0;
-                       $this->mTrxIdleCallbacks = []; // bug 65263
-                       $this->mTrxPreCommitCallbacks = []; // bug 65263
-                       wfDebug( "Connection lost, reconnecting...\n" );
-                       # Stash the last error values since ping() might clear them
+                       $recoverable = $this->canRecoverFromDisconnect( $sql, $priorWritesPending );
+                       # Stash the last error values before anything might clear them
                        $lastError = $this->lastError();
                        $lastErrno = $this->lastErrno();
-                       if ( $this->ping() ) {
+                       # Update state tracking to reflect transaction loss due to disconnection
+                       $this->handleTransactionLoss();
+                       wfDebug( "Connection lost, reconnecting...\n" );
+                       if ( $this->reconnect() ) {
                                wfDebug( "Reconnected\n" );
-                               $server = $this->getServer();
-                               $msg = __METHOD__ . ": lost connection to $server; reconnected";
+                               $msg = __METHOD__ . ": lost connection to {$this->getServer()}; reconnected";
                                wfDebugLog( 'DBPerformance', "$msg:\n" . wfBacktrace( true ) );
 
-                               if ( ( $hadTrx && !$isNoopCommit ) || $this->mNamedLocksHeld ) {
-                                       # Leave $ret as false and let an error be reported.
-                                       # Callers may catch the exception and continue to use the DB.
-                                       $this->reportQueryError( $lastError, $lastErrno, $sql, $fname, $tempIgnore );
+                               if ( !$recoverable ) {
+                                       # Callers may catch the exception and continue to use the DB
+                                       $this->reportQueryError( $lastError, $lastErrno, $sql, $fname );
                                } else {
-                                       # Should be safe to silently retry (no trx/callbacks/locks)
+                                       # Should be safe to silently retry the query
                                        $startTime = microtime( true );
                                        $ret = $this->doQuery( $commentedSql );
                                        $queryRuntime = microtime( true ) - $startTime;
@@ -900,6 +896,17 @@ abstract class DatabaseBase implements IDatabase {
                }
 
                if ( false === $ret ) {
+                       # Deadlocks cause the entire transaction to abort, not just the statement.
+                       # http://dev.mysql.com/doc/refman/5.7/en/innodb-error-handling.html
+                       # https://www.postgresql.org/docs/9.1/static/explicit-locking.html
+                       if ( $this->wasDeadlock() ) {
+                               if ( $this->explicitTrxActive() || $priorWritesPending ) {
+                                       $tempIgnore = false; // not recoverable
+                               }
+                               # Update state tracking to reflect transaction loss
+                               $this->handleTransactionLoss();
+                       }
+
                        $this->reportQueryError(
                                $this->lastError(), $this->lastErrno(), $sql, $fname, $tempIgnore );
                }
@@ -918,6 +925,40 @@ abstract class DatabaseBase implements IDatabase {
                return $res;
        }
 
+       private function canRecoverFromDisconnect( $sql, $priorWritesPending ) {
+               # Transaction dropped; this can mean lost writes, or REPEATABLE-READ snapshots.
+               # Dropped connections also mean that named locks are automatically released.
+               # Only allow error suppression in autocommit mode or when the lost transaction
+               # didn't matter anyway (aside from DBO_TRX snapshot loss).
+               if ( $this->mNamedLocksHeld ) {
+                       return false; // possible critical section violation
+               } elseif ( $sql === 'COMMIT' ) {
+                       return !$priorWritesPending; // nothing written anyway? (T127428)
+               } elseif ( $sql === 'ROLLBACK' ) {
+                       return true; // transaction lost...which is also what was requested :)
+               } elseif ( $this->explicitTrxActive() ) {
+                       return false; // don't drop atomocity
+               } elseif ( $priorWritesPending ) {
+                       return false; // prior writes lost from implicit transaction
+               }
+
+               return true;
+       }
+
+       private function handleTransactionLoss() {
+               $this->mTrxLevel = 0;
+               $this->mTrxIdleCallbacks = []; // bug 65263
+               $this->mTrxPreCommitCallbacks = []; // bug 65263
+               try {
+                       // Handle callbacks in mTrxEndCallbacks
+                       $this->runOnTransactionIdleCallbacks( self::TRIGGER_ROLLBACK );
+                       return null;
+               } catch ( Exception $e ) {
+                       // Already logged; move on...
+                       return $e;
+               }
+       }
+
        public function reportQueryError( $error, $errno, $sql, $fname, $tempIgnore = false ) {
                if ( $this->ignoreErrors() || $tempIgnore ) {
                        wfDebug( "SQL ERROR (ignored): $error\n" );
@@ -1823,7 +1864,7 @@ abstract class DatabaseBase implements IDatabase {
        /**
         * Gets an array of aliased table names
         *
-        * @param array $tables Array( [alias] => table )
+        * @param array $tables [ [alias] => table ]
         * @return string[] See tableNameWithAlias()
         */
        public function tableNamesWithAlias( $tables ) {
@@ -1857,7 +1898,7 @@ abstract class DatabaseBase implements IDatabase {
        /**
         * Gets an array of aliased field names
         *
-        * @param array $fields Array( [alias] => field )
+        * @param array $fields [ [alias] => field ]
         * @return string[] See fieldNameWithAlias()
         */
        public function fieldNamesWithAlias( $fields ) {
@@ -2509,6 +2550,7 @@ abstract class DatabaseBase implements IDatabase {
         *
         * @param integer $trigger IDatabase::TRIGGER_* constant
         * @since 1.20
+        * @throws Exception
         */
        public function runOnTransactionIdleCallbacks( $trigger ) {
                if ( $this->suppressPostCommitCallbacks ) {
@@ -2516,7 +2558,7 @@ abstract class DatabaseBase implements IDatabase {
                }
 
                $autoTrx = $this->getFlag( DBO_TRX ); // automatic begin() enabled?
-
+               /** @var Exception $e */
                $e = $ePrior = null; // last exception
                do { // callbacks may add callbacks :)
                        $callbacks = array_merge(
@@ -2642,13 +2684,13 @@ abstract class DatabaseBase implements IDatabase {
                                        "$fname: Transaction already in progress (from {$this->mTrxFname}), " .
                                                " performing implicit commit!"
                                );
-                       } else {
+                       } elseif ( $this->mTrxDoneWrites ) {
                                // The transaction was automatic and has done write operations
-                               if ( $this->mTrxDoneWrites ) {
-                                       wfLogDBError( "$fname: Automatic transaction with writes in progress" .
+                               throw new DBUnexpectedError(
+                                       $this,
+                                       "$fname: Automatic transaction with writes in progress" .
                                                " (from {$this->mTrxFname}), performing implicit commit!\n"
-                                       );
-                               }
+                               );
                        }
 
                        $this->runOnTransactionPreCommitCallbacks();
@@ -2718,7 +2760,10 @@ abstract class DatabaseBase implements IDatabase {
                                wfWarn( "$fname: No transaction to commit, something got out of sync!" );
                                return; // nothing to do
                        } elseif ( $this->mTrxAutomatic ) {
-                               wfWarn( "$fname: Explicit commit of implicit transaction. Something may be out of sync!" );
+                               throw new DBUnexpectedError(
+                                       $this,
+                                       "$fname: Explicit commit of implicit transaction."
+                               );
                        }
                }
 
@@ -2785,11 +2830,20 @@ abstract class DatabaseBase implements IDatabase {
         */
        protected function doRollback( $fname ) {
                if ( $this->mTrxLevel ) {
-                       $this->query( 'ROLLBACK', $fname, true );
+                       # Disconnects cause rollback anyway, so ignore those errors
+                       $ignoreErrors = true;
+                       $this->query( 'ROLLBACK', $fname, $ignoreErrors );
                        $this->mTrxLevel = 0;
                }
        }
 
+       /**
+        * @return bool
+        */
+       protected function explicitTrxActive() {
+               return $this->mTrxLevel && ( $this->mTrxAtomicLevels || !$this->mTrxAutomatic );
+       }
+
        /**
         * Creates a new table with structure copied from existing table
         * Note that unlike most database abstraction functions, this function does not
@@ -2891,6 +2945,19 @@ abstract class DatabaseBase implements IDatabase {
        }
 
        public function ping() {
+               try {
+                       // This will reconnect if possible, or error out if not
+                       $this->query( "SELECT 1 AS ping", __METHOD__ );
+                       return true;
+               } catch ( DBError $e ) {
+                       return false;
+               }
+       }
+
+       /**
+        * @return bool
+        */
+       protected function reconnect() {
                # Stub. Not essential to override.
                return true;
        }
index 5b15147..87330b0 100644 (file)
@@ -201,10 +201,4 @@ class DatabaseMysql extends DatabaseMysqlBase {
 
                return mysql_real_escape_string( $s, $conn );
        }
-
-       protected function mysqlPing() {
-               $conn = $this->getBindingHandle();
-
-               return mysql_ping( $conn );
-       }
 }
index ee84224..6380fe7 100644 (file)
@@ -570,14 +570,7 @@ abstract class DatabaseMysqlBase extends Database {
         * @return string
         */
        function strencode( $s ) {
-               $sQuoted = $this->mysqlRealEscapeString( $s );
-
-               if ( $sQuoted === false ) {
-                       $this->ping();
-                       $sQuoted = $this->mysqlRealEscapeString( $s );
-               }
-
-               return $sQuoted;
+               return $this->mysqlRealEscapeString( $s );
        }
 
        /**
@@ -606,18 +599,7 @@ abstract class DatabaseMysqlBase extends Database {
                return strlen( $name ) && $name[0] == '`' && substr( $name, -1, 1 ) == '`';
        }
 
-       /**
-        * @return bool
-        */
-       function ping() {
-               $ping = $this->mysqlPing();
-               if ( $ping ) {
-                       // Connection was good or lost but reconnected...
-                       // @note: mysqlnd (php 5.6+) does not support this (PHP bug 52561)
-                       return true;
-               }
-
-               // Try a full disconnect/reconnect cycle if ping() failed
+       function reconnect() {
                $this->closeConnection();
                $this->mOpened = false;
                $this->mConn = false;
@@ -626,13 +608,6 @@ abstract class DatabaseMysqlBase extends Database {
                return true;
        }
 
-       /**
-        * Ping a server connection or reconnect if there is no connection
-        *
-        * @return bool
-        */
-       abstract protected function mysqlPing();
-
        function getLag() {
                if ( $this->getLagDetectionMethod() === 'pt-heartbeat' ) {
                        return $this->getLagFromPtHeartbeat();
@@ -1186,12 +1161,6 @@ abstract class DatabaseMysqlBase extends Database {
                return $this->lastErrno() == 1205;
        }
 
-       /**
-        * Determines if the last query error was something that should be dealt
-        * with by pinging the connection and reissuing the query
-        *
-        * @return bool
-        */
        function wasErrorReissuable() {
                return $this->lastErrno() == 2013 || $this->lastErrno() == 2006;
        }
index d45805a..cb580cc 100644 (file)
@@ -309,12 +309,6 @@ class DatabaseMysqli extends DatabaseMysqlBase {
                return $conn->real_escape_string( $s );
        }
 
-       protected function mysqlPing() {
-               $conn = $this->getBindingHandle();
-
-               return $conn->ping();
-       }
-
        /**
         * Give an id for the connection
         *
index 9dcbd7f..43592e2 100644 (file)
@@ -1156,7 +1156,6 @@ interface IDatabase {
 
        /**
         * Determines how long the server has been up
-        * STUB
         *
         * @return int
         */
@@ -1164,7 +1163,6 @@ interface IDatabase {
 
        /**
         * Determines if the last failure was due to a deadlock
-        * STUB
         *
         * @return bool
         */
@@ -1172,16 +1170,14 @@ interface IDatabase {
 
        /**
         * Determines if the last failure was due to a lock timeout
-        * STUB
         *
         * @return bool
         */
        public function wasLockTimeout();
 
        /**
-        * Determines if the last query error was something that should be dealt
-        * with by pinging the connection and reissuing the query.
-        * STUB
+        * Determines if the last query error was due to a dropped connection and should
+        * be dealt with by pinging the connection and reissuing the query.
         *
         * @return bool
         */
@@ -1189,7 +1185,6 @@ interface IDatabase {
 
        /**
         * Determines if the last failure was due to the database being read-only.
-        * STUB
         *
         * @return bool
         */
index 053f9f8..4078a39 100644 (file)
@@ -31,15 +31,16 @@ use MediaWiki\Logger\LoggerFactory;
  * @ingroup Database
  */
 abstract class LBFactory implements DestructibleService {
-
        /** @var ChronologyProtector */
        protected $chronProt;
-
        /** @var TransactionProfiler */
        protected $trxProfiler;
-
        /** @var LoggerInterface */
-       protected $logger;
+       protected $trxLogger;
+       /** @var BagOStuff */
+       protected $srvCache;
+       /** @var WANObjectCache */
+       protected $wanCache;
 
        /** @var string|bool Reason all LBs are read-only or false if not */
        protected $readOnlyReason = false;
@@ -49,15 +50,28 @@ abstract class LBFactory implements DestructibleService {
        /**
         * Construct a factory based on a configuration array (typically from $wgLBFactoryConf)
         * @param array $conf
+        * @TODO: inject objects via dependency framework
         */
        public function __construct( array $conf ) {
                if ( isset( $conf['readOnlyReason'] ) && is_string( $conf['readOnlyReason'] ) ) {
                        $this->readOnlyReason = $conf['readOnlyReason'];
                }
-
                $this->chronProt = $this->newChronologyProtector();
                $this->trxProfiler = Profiler::instance()->getTransactionProfiler();
-               $this->logger = LoggerFactory::getInstance( 'DBTransaction' );
+               // Use APC/memcached style caching, but avoids loops with CACHE_DB (T141804)
+               $cache = ObjectCache::getLocalServerInstance();
+               if ( $cache->getQoS( $cache::ATTR_EMULATION ) > $cache::QOS_EMULATION_SQL ) {
+                       $this->srvCache = $cache;
+               } else {
+                       $this->srvCache = new EmptyBagOStuff();
+               }
+               $wCache = ObjectCache::getMainWANInstance();
+               if ( $wCache->getQoS( $wCache::ATTR_EMULATION ) > $wCache::QOS_EMULATION_SQL ) {
+                       $this->wanCache = $wCache;
+               } else {
+                       $this->wanCache = WANObjectCache::newEmpty();
+               }
+               $this->trxLogger = LoggerFactory::getInstance( 'DBTransaction' );
        }
 
        /**
@@ -261,7 +275,7 @@ abstract class LBFactory implements DestructibleService {
                        foreach ( $callersByDB as $db => $callers ) {
                                $msg .= "$db: " . implode( '; ', $callers ) . "\n";
                        }
-                       $this->logger->info( $msg );
+                       $this->trxLogger->info( $msg );
                }
        }
 
index 32b1a0f..0f3ca93 100644 (file)
@@ -317,7 +317,9 @@ class LBFactoryMulti extends LBFactory {
                        'servers' => $this->makeServerArray( $template, $loads, $groupLoads ),
                        'loadMonitor' => $this->loadMonitorClass,
                        'readOnlyReason' => $readOnlyReason,
-                       'trxProfiler' => $this->trxProfiler
+                       'trxProfiler' => $this->trxProfiler,
+                       'srvCache' => $this->srvCache,
+                       'wanCache' => $this->wanCache
                ] );
        }
 
index 1b0a1f3..14baf2e 100644 (file)
@@ -84,12 +84,7 @@ class LBFactorySimple extends LBFactory {
                        ] ];
                }
 
-               return new LoadBalancer( [
-                       'servers' => $servers,
-                       'loadMonitor' => $this->loadMonitorClass,
-                       'readOnlyReason' => $this->readOnlyReason,
-                       'trxProfiler' => $this->trxProfiler
-               ] );
+               return $this->newLoadBalancer( $servers );
        }
 
        /**
@@ -118,12 +113,7 @@ class LBFactorySimple extends LBFactory {
                        throw new MWException( __METHOD__ . ": Unknown cluster \"$cluster\"" );
                }
 
-               return new LoadBalancer( [
-                       'servers' => $wgExternalServers[$cluster],
-                       'loadMonitor' => $this->loadMonitorClass,
-                       'readOnlyReason' => $this->readOnlyReason,
-                       'trxProfiler' => $this->trxProfiler
-               ] );
+               return $this->newLoadBalancer( $wgExternalServers[$cluster] );
        }
 
        /**
@@ -141,6 +131,17 @@ class LBFactorySimple extends LBFactory {
                return $this->extLBs[$cluster];
        }
 
+       private function newLoadBalancer( array $servers ) {
+               return new LoadBalancer( [
+                       'servers' => $servers,
+                       'loadMonitor' => $this->loadMonitorClass,
+                       'readOnlyReason' => $this->readOnlyReason,
+                       'trxProfiler' => $this->trxProfiler,
+                       'srvCache' => $this->srvCache,
+                       'wanCache' => $this->wanCache
+               ] );
+       }
+
        /**
         * Execute a function for each tracked load balancer
         * The callback is called with the load balancer as the first parameter,
index 79ca3a7..14c1c28 100644 (file)
@@ -37,7 +37,9 @@ class LBFactorySingle extends LBFactory {
 
                $this->lb = new LoadBalancerSingle( [
                        'readOnlyReason' => $this->readOnlyReason,
-                       'trxProfiler' => $this->trxProfiler
+                       'trxProfiler' => $this->trxProfiler,
+                       'srvCache' => $this->srvCache,
+                       'wanCache' => $this->wanCache
                ] + $conf );
        }
 
@@ -106,7 +108,9 @@ class LoadBalancerSingle extends LoadBalancer {
                                        'load' => 1,
                                ]
                        ],
-                       'trxProfiler' => $this->trxProfiler
+                       'trxProfiler' => isset( $params['trxProfiler'] ) ? $params['trxProfiler'] : null,
+                       'srvCache' => isset( $params['srvCache'] ) ? $params['srvCache'] : null,
+                       'wanCache' => isset( $params['wanCache'] ) ? $params['wanCache'] : null
                ] );
 
                if ( isset( $params['readOnlyReason'] ) ) {
index 1269c3e..a7c486c 100644 (file)
@@ -91,6 +91,8 @@ class LoadBalancer {
         *  - servers : Required. Array of server info structures.
         *  - loadMonitor : Name of a class used to fetch server lag and load.
         *  - readOnlyReason : Reason the master DB is read-only if so [optional]
+        *  - srvCache : BagOStuff object [optional]
+        *  - wanCache : WANObjectCache object [optional]
         * @throws MWException
         */
        public function __construct( array $params ) {
@@ -138,21 +140,16 @@ class LoadBalancer {
                        }
                }
 
-               // Use APC/memcached style caching, but avoids loops with CACHE_DB (T141804)
-               // @TODO: inject these in via LBFactory at some point
-               $cache = ObjectCache::getLocalServerInstance();
-               if ( $cache->getQoS( $cache::ATTR_EMULATION ) > $cache::QOS_EMULATION_SQL ) {
-                       $this->srvCache = $cache;
+               if ( isset( $params['srvCache'] ) ) {
+                       $this->srvCache = $params['srvCache'];
                } else {
                        $this->srvCache = new EmptyBagOStuff();
                }
-               $wCache = ObjectCache::getMainWANInstance();
-               if ( $wCache->getQoS( $wCache::ATTR_EMULATION ) > $wCache::QOS_EMULATION_SQL ) {
-                       $this->wanCache = $wCache;
+               if ( isset( $params['wanCache'] ) ) {
+                       $this->wanCache = $params['wanCache'];
                } else {
                        $this->wanCache = WANObjectCache::newEmpty();
                }
-
                if ( isset( $params['trxProfiler'] ) ) {
                        $this->trxProfiler = $params['trxProfiler'];
                } else {
index 4a6ac8e..baec396 100644 (file)
@@ -555,7 +555,6 @@ class DifferenceEngine extends ContextSource {
                        // Build the link
                        if ( $rcid ) {
                                $this->getOutput()->preventClickjacking();
-                               $this->getOutput()->addModuleStyles( 'mediawiki.page.patrol' );
                                if ( $wgEnableAPI && $wgEnableWriteAPI
                                        && $user->isAllowed( 'writeapi' )
                                ) {
index bebd915..0a174fe 100644 (file)
@@ -91,7 +91,7 @@ class MWException extends Exception {
                                is_string( $hook ) ||
                                ( is_array( $hook ) && count( $hook ) >= 2 && is_string( $hook[0] ) )
                        ) {
-                               // 'function' or array( 'class', hook' )
+                               // 'function' or [ 'class', 'hook' ]
                                $result = call_user_func_array( $hook, $callargs );
                        } else {
                                $result = null;
index e5ded45..b61b08d 100644 (file)
@@ -150,8 +150,7 @@ abstract class DBLockManager extends QuorumLockManager {
                if ( !isset( $this->conns[$lockDb] ) ) {
                        $db = null;
                        if ( $lockDb === 'localDBMaster' ) {
-                               $lb = wfGetLBFactory()->getMainLB( $this->domain );
-                               $db = $lb->getConnection( DB_MASTER, [], $this->domain );
+                               $db = $this->getLocalLB()->getConnection( DB_MASTER, [], $this->domain );
                        } elseif ( isset( $this->dbServers[$lockDb] ) ) {
                                $config = $this->dbServers[$lockDb];
                                $db = DatabaseBase::factory( $config['type'], $config );
@@ -178,6 +177,13 @@ abstract class DBLockManager extends QuorumLockManager {
                return $this->conns[$lockDb];
        }
 
+       /**
+        * @return LoadBalancer
+        */
+       protected function getLocalLB() {
+               return wfGetLBFactory()->getMainLB( $this->domain );
+       }
+
        /**
         * Do additional initialization for new lock DB connection
         *
@@ -249,10 +255,11 @@ class MySqlLockManager extends DBLockManager {
                self::LOCK_EX => self::LOCK_EX
        ];
 
-       /**
-        * @param string $lockDb
-        * @param IDatabase $db
-        */
+       protected function getLocalLB() {
+               // Use a separate connection so releaseAllLocks() doesn't rollback the main trx
+               return wfGetLBFactory()->newMainLB( $this->domain );
+       }
+
        protected function initConnection( $lockDb, IDatabase $db ) {
                # Let this transaction see lock rows from other transactions
                $db->query( "SET SESSION TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;" );
index 08a40eb..d515b05 100644 (file)
@@ -177,8 +177,8 @@ class RepoGroup {
         * @param array $inputItems An array of titles, or an array of findFile() options with
         *    the "title" option giving the title. Example:
         *
-        *     $findItem = array( 'title' => $title, 'private' => true );
-        *     $findBatch = array( $findItem );
+        *     $findItem = [ 'title' => $title, 'private' => true ];
+        *     $findBatch = [ $findItem ];
         *     $repo->findFiles( $findBatch );
         *
         *    No title should appear in $items twice, as the result use titles as keys
index a7acd8b..ff37e24 100644 (file)
@@ -275,14 +275,12 @@ class HTMLForm extends ContextSource {
 
                switch ( $displayFormat ) {
                        case 'vform':
-                               $reflector = new ReflectionClass( 'VFormHTMLForm' );
-                               return $reflector->newInstanceArgs( $arguments );
+                               return ObjectFactory::constructClassInstance( VFormHTMLForm::class, $arguments );
                        case 'ooui':
-                               $reflector = new ReflectionClass( 'OOUIHTMLForm' );
-                               return $reflector->newInstanceArgs( $arguments );
+                               return ObjectFactory::constructClassInstance( OOUIHTMLForm::class, $arguments );
                        default:
-                               $reflector = new ReflectionClass( 'HTMLForm' );
-                               $form = $reflector->newInstanceArgs( $arguments );
+                               /** @var HTMLForm $form */
+                               $form = ObjectFactory::constructClassInstance( HTMLForm::class, $arguments );
                                $form->setDisplayFormat( $displayFormat );
                                return $form;
                }
index ec1bd84..f39f54b 100644 (file)
@@ -354,7 +354,7 @@ class HTMLFormFieldCloner extends HTMLFormField {
                        );
                }
 
-               $template = $this->getInputHTMLForKey( $this->uniqueId, null );
+               $template = $this->getInputHTMLForKey( $this->uniqueId, [] );
                $html = Html::rawElement( 'ul', [
                        'id' => "mw-htmlform-cloner-list-{$this->mID}",
                        'class' => 'mw-htmlform-cloner-ul',
index accc42f..770d3bf 100644 (file)
@@ -87,7 +87,11 @@ class MssqlUpdater extends DatabaseUpdater {
                        [ 'updateSchema', 'recentchanges', 'recentchanges-drop-fks',
                                'patch-recentchanges-drop-fks.sql' ],
                        [ 'updateSchema', 'logging', 'logging-drop-fks', 'patch-logging-drop-fks.sql' ],
-                       [ 'updateSchema', 'archive', 'archive-drop-fks', 'patch-archive-drop-fks.sql' ]
+                       [ 'updateSchema', 'archive', 'archive-drop-fks', 'patch-archive-drop-fks.sql' ],
+
+                       // 1.28
+                       [ 'addIndex', 'recentchanges', 'rc_name_type_patrolled_timestamp',
+                               'patch-add-rc_name_type_patrolled_timestamp_index.sql' ],
                ];
        }
 
index d414d90..719b66a 100644 (file)
@@ -283,6 +283,10 @@ class MysqlUpdater extends DatabaseUpdater {
                        [ 'addIndex', 'categorylinks', 'cl_collation_ext',
                                'patch-add-cl_collation_ext_index.sql' ],
                        [ 'doCollationUpdate' ],
+
+                       // 1.28
+                       [ 'addIndex', 'recentchanges', 'rc_name_type_patrolled_timestamp',
+                               'patch-add-rc_name_type_patrolled_timestamp_index.sql' ],
                ];
        }
 
index 334256b..8075aac 100644 (file)
@@ -113,6 +113,10 @@ class OracleUpdater extends DatabaseUpdater {
                        [ 'dropTable', 'msg_resource' ],
                        [ 'addField', 'watchlist', 'wl_id', 'patch-watchlist-wl_id.sql' ],
 
+                       // 1.28
+                       [ 'addIndex', 'recentchanges', 'rc_name_type_patrolled_timestamp',
+                               'patch-add-rc_name_type_patrolled_timestamp_index.sql' ],
+
                        // KEEP THIS AT THE BOTTOM!!
                        [ 'doRebuildDuplicateFunction' ],
 
index a3b50ac..be94d91 100644 (file)
@@ -433,6 +433,10 @@ class PostgresUpdater extends DatabaseUpdater {
                                'addPgField', 'watchlist', 'wl_id',
                                "INTEGER NOT NULL PRIMARY KEY DEFAULT nextval('watchlist_wl_id_seq')"
                        ],
+
+                       // 1.28
+                       [ 'addPgIndex', 'recentchanges', 'rc_name_type_patrolled_timestamp',
+                               '( rc_namespace, rc_type, rc_patrolled, rc_timestamp )' ],
                ];
        }
 
index 86dccd7..1c6e6eb 100644 (file)
@@ -152,6 +152,10 @@ class SqliteUpdater extends DatabaseUpdater {
                        [ 'addIndex', 'categorylinks', 'cl_collation_ext',
                                'patch-add-cl_collation_ext_index.sql' ],
                        [ 'doCollationUpdate' ],
+
+                       // 1.28
+                       [ 'addIndex', 'recentchanges', 'rc_name_type_patrolled_timestamp',
+                               'patch-add-rc_name_type_patrolled_timestamp_index.sql' ],
                ];
        }
 
index cc31402..4e34c7d 100644 (file)
        "config-ns-site-name": "Същото като името на уикито: $1",
        "config-ns-other": "Друго (уточняване)",
        "config-ns-other-default": "МоетоУики",
-       "config-project-namespace-help": "Следвайки примера на Уикипедия, много уикита съхраняват страниците си с правила в \"'''именно пространство на проекта'''\", отделно от основното съдържание.\nВсички заглавия на страниците в това именно пространство започват с определена представка, която може да бъде зададена тук.\nОбикновено представката произлиза от името на уикито, но не може да съдържа символи като \"#\" или \":\".",
+       "config-project-namespace-help": "Следвайки примера на Уикипедия, много уикита съхраняват страниците си с правила в '''именно пространство на проекта''', отделно от основното съдържание.\nВсички заглавия на страниците в това именно пространство започват с определена представка, която може да бъде зададена тук.\nОбикновено представката произлиза от името на уикито, но не може да съдържа символи като \"#\" или \":\".",
        "config-ns-invalid": "Посоченото именно пространство \"<nowiki>$1</nowiki>\" е невалидно.\nНеобходимо е да бъде посочено друго.",
        "config-ns-conflict": "Посоченото именно пространство \"<nowiki>$1</nowiki>\" е в конфликт с използваното по подразбиране именно пространство MediaWiki.\nНеобходимо е да се посочи друго именно пространство.",
        "config-admin-box": "Администраторска сметка",
        "config-subscribe": "Абониране за [https://lists.wikimedia.org/mailman/listinfo/mediawiki-announce пощенския списък за нови версии].",
        "config-subscribe-help": "Това е пощенски списък с малко трафик, който се използва за съобщения при излизане на нови версии, както и за важни проблеми със сигурността.\nАбонирането е препоръчително, както и надграждането на инсталацията на МедияУики при излизането на нова версия.",
        "config-subscribe-noemail": "Опитахте да се абонирате за пощенския списък за нови версии без да посочите адрес за електронна поща.\nНеобходимо е да се предостави адрес за електронна поща, в случай че желаете да се абонирате за пощенския списък.",
+       "config-pingback": "Споделяне на данни за инсталацията с разработчиците на МедияУики.",
+       "config-pingback-help": "Ако изберете тази настройка, МедияУики периодично ще пингва https://www.mediawiki.org с основна информация за тази инсталация на МедияУики. Информацията включва например, тип на операционната система, версията на PHP и избраната СУБД. Фондация Уикимедия споделя тези данни с разработчиците на МедияУики, за да им помогне в бъдещото развитие на софтуера. Следните данни ще бъдат изпратени за вашата система:\n<pre>$1</pre>",
        "config-almost-done": "Инсталацията е почти готова!\nВъзможно е пропускане на оставащата конфигурация и моментално инсталиране на уикито.",
        "config-optional-continue": "Задаване на допълнителни въпроси.",
        "config-optional-skip": "Достатъчно, инсталиране на уикито.",
        "config-install-keys": "Генериране на тайни ключове",
        "config-insecure-keys": "'''Предупреждение:''' {{PLURAL:$2|Сигурният ключ, създаден по време на инсталацията, не е напълно надежден|Сигурните ключове, създадени по време на инсталацията, не са напълно надеждни}} $1 . Обмислете да {{PLURAL:$2|го|ги}} смените ръчно.",
        "config-install-updates": "Предотвратяване стартирането на ненужни актуализации",
+       "config-install-updates-failed": "<strong>Грешка:</strong> Вмъкването на обновяващи ключове в таблиците се провали по следната причина: $1",
        "config-install-sysop": "Създаване на администраторска сметка",
        "config-install-subscribe-fail": "Невъзможно беше абонирането за mediawiki-announce: $1",
        "config-install-subscribe-notpossible": "не е инсталиран cURL и <code>allow_url_fopen</code> не е налична.",
        "config-install-mainpage": "Създаване на Началната страница със съдържание по подразбиране",
        "config-install-extension-tables": "Създаване на таблици за включените разширения",
        "config-install-mainpage-failed": "Вмъкването на Началната страница беше невъзможно: $1",
-       "config-install-done": "'''Поздравления!'''\nИнсталирането на МедияУики приключи успешно.\n\nИнсталаторът създаде файл <code>LocalSettings.php</code>.\nТой съдържа всичката необходима основна конфигурация на уикито.\n\nНеобходимо е той да бъде изтеглен и поставен в основната директория на уикито (директорията, в която е и index.php). Изтеглянето би трябвало да започне автоматично.\n\nАко изтеглянето не започне автоматично или е било прекратено, файлът може да бъде изтеглен чрез щракване на препратката по-долу:\n\n$3\n\n'''Забележка''': Ако това не бъде извършено сега, генерираният конфигурационен файл няма да е достъпен на по-късен етап ако не бъде изтеглен сега или инсталацията приключи без изтеглянето му.\n\nКогато файлът вече е в основната директория, '''[$2 уикито ще е достъпно на този адрес]'''.",
+       "config-install-done": "<strong>Поздравления!</strong>\nИнсталирането на МедияУики приключи успешно.\n\nИнсталаторът създаде файл <code>LocalSettings.php</code>.\nТой съдържа всичката необходима основна конфигурация на уикито.\n\nНеобходимо е той да бъде изтеглен и поставен в основната директория на уикито (директорията, в която е и index.php). Изтеглянето би трябвало да започне автоматично.\n\nАко изтеглянето не започне автоматично или е било прекратено, файлът може да бъде изтеглен чрез щракване на препратката по-долу:\n\n$3\n\n<strong>Забележка:</strong> Ако това не бъде извършено сега, генерираният конфигурационен файл няма да е достъпен на по-късен етап ако не бъде изтеглен сега или инсталацията приключи без изтеглянето му.\n\nКогато файлът вече е в основната директория, <strong>[$2 уикито ще е достъпно на този адрес]</strong>.",
+       "config-install-done-path": "<strong>Поздравления!</strong>\nИнсталирането на МедияУики приключи успешно.\n\nИнсталаторът създаде файл <code>LocalSettings.php</code>.\nТой съдържа всички ваши настройки.\n\nНеобходимо е той да бъде изтеглен и поставен в <code>$4</code>. Изтеглянето би трябвало да започне автоматично.\n\nАко изтеглянето не започне автоматично или е било прекратено, файлът може да бъде изтеглен чрез щракване на препратката по-долу:\n\n$3\n\n<strong>Забележка:</strong> Ако това не бъде направено сега, генерираният конфигурационен файл няма да е достъпен на по-късен етап ако не бъде изтеглен сега или инсталацията приключи без изтеглянето му.\n\nКогато файлът вече е в основната директория, <strong>[$2 уикито ще е достъпно на този адрес]</strong>.",
        "config-download-localsettings": "Изтегляне на <code>LocalSettings.php</code>",
        "config-help": "помощ",
        "config-nofile": "Файлът „$1“ не може да бъде открит. Да не е бил изтрит?",
        "config-extension-link": "Знаете ли, че това уики поддържа [https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Extensions разширения]?\n\nМожете да разгледате [https://www.mediawiki.org/wiki/Special:MyLanguage/Category:Extensions_by_category разширенията по категория] или [https://www.mediawiki.org/wiki/Extension_Matrix Матрицата на разширенията] за пълен списък на разширенията.",
-       "mainpagetext": "'''Уикито беше успешно инсталирано.'''",
+       "mainpagetext": "<strong>Уикито беше успешно инсталирано.</strong>",
        "mainpagedocfooter": "Разгледайте [https://meta.wikimedia.org/wiki/Help:Contents ръководството] за подробна информация относно използването на уики софтуера.\n\n== Първи стъпки ==\n* [https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Configuration_settings Настройки за конфигуриране]\n* [https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:FAQ ЧЗВ за МедияУики]\n* [https://lists.wikimedia.org/mailman/listinfo/mediawiki-announce Пощенски списък относно нови версии на МедияУики]\n* [https://www.mediawiki.org/wiki/Special:MyLanguage/Localisation#Translation_resources Локализиране на МедияУики]\n* [https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Combating_spam Научете как да се справяте със спама във вашето уики]"
 }
diff --git a/includes/installer/i18n/dty.json b/includes/installer/i18n/dty.json
new file mode 100644 (file)
index 0000000..a986e00
--- /dev/null
@@ -0,0 +1,52 @@
+{
+       "@metadata": {
+               "authors": [
+                       "राम प्रसाद जोशी"
+               ]
+       },
+       "config-desc": "मेडियाविकिको लागि स्थापक",
+       "config-title": "मेडिया विकि $1 स्थापना",
+       "config-information": "जानकारी",
+       "config-localsettings-upgrade": "<code>LocalSettings.php</code> फाइल पाइयो ।\nयै स्थापनालाई अपग्रेड गर्न, तलीखाइ दिया  बक्समी <code>$wgUpgradeKey</code>  को मान दर्ज गर ।\nतम <code>LocalSettings.php</code> मा भेट्टे हौ ।",
+       "config-localsettings-cli-upgrade": "<code>LocalSettings.php</code> फाइल पाइयो ।\nयै स्थापनालाई अपग्रेड गद्द, बदलामी कृपया यैलाई चलाओ <code>update.php</code>",
+       "config-localsettings-key": "नवीनीकरण साँचो",
+       "config-localsettings-badkey": "तमले प्रोभाइट गर्याको नवनिकरण साँचो मान्य छैन",
+       "config-upgrade-key-missing": "An existing installation of MediaWiki has been detected.\nTo upgrade this installation, please put the following line at the bottom of your <code>LocalSettings.php</code>:\n\n$1",
+       "config-localsettings-incomplete": "The existing <code>LocalSettings.php</code> appears to be incomplete.\nThe $1 variable is not set.\nPlease change <code>LocalSettings.php</code> so that this variable is set, and click \"{{int:Config-continue}}\".",
+       "config-localsettings-connection-error": "An error was encountered when connecting to the database using the settings specified in <code>LocalSettings.php</code>. Please fix these settings and try again.\n\n$1",
+       "config-session-error": "Error starting session: $1",
+       "config-session-expired": "Your session data seems to have expired.\nSessions are configured for a lifetime of $1.\nYou can increase this by setting <code>session.gc_maxlifetime</code> in php.ini.\nRestart the installation process.",
+       "config-no-session": "तमरो सेसन डाटा मेटिया छ!\nतमरो php चेक गर। ini र make sure <code>session.save_path</code> is set to an appropriate directory.",
+       "config-your-language": "तमरो भाषा:",
+       "config-your-language-help": "इन्स्टाल गर्दा उपयोग गद्दे भाषा छान ।",
+       "config-wiki-language": "विकि भाषाहरू",
+       "config-wiki-language-help": "Select the language that the wiki will predominantly be written in.",
+       "config-back": "← पछाडी",
+       "config-continue": "जारी राख्या",
+       "config-page-language": "भाषा",
+       "config-page-welcome": "मिडीयाविकिमी तमलाई स्वागत छ!",
+       "config-page-dbconnect": "डेटाबेससँग सम्बन्ध बनाउन्या",
+       "config-page-upgrade": "मौजूदा स्थापनाको नवीनीकरण",
+       "config-page-dbsettings": "डेटावेस सेटिङ",
+       "config-page-name": "नाऊ",
+       "config-page-options": "विकल्पहरू",
+       "config-page-install": "स्थापना गद्दे",
+       "config-page-complete": "पूरा भयो !",
+       "config-page-restart": "स्थापना फेरि सुरु गद्दे",
+       "config-page-readme": "थप पड्डे",
+       "config-page-releasenotes": "प्रकाशन टिप्पणी",
+       "config-page-copying": "कपि हून लाग्याको छ",
+       "config-page-upgradedoc": "अद्यावधिक गरिदै",
+       "config-page-existingwiki": "विकि बन्द हुँदै",
+       "config-help-restart": "Do you want to clear all saved data that you have entered and restart the installation process?",
+       "config-restart": "हुन्छ, पुनः सुचारू गद्दे",
+       "config-welcome": "=== Environmental checks ===\nBasic checks will now be performed to see if this environment is suitable for MediaWiki installation.\nRemember to include this information if you seek support on how to complete the installation.",
+       "config-copyright": "=== Copyright and Terms ===\n\n$1\n\nThis program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version.\n\nThis program is distributed in the hope that it will be useful, but <strong>without any warranty</strong>; without even the implied warranty of <strong>merchantability</strong> or <strong>fitness for a particular purpose</strong>.\nSee the GNU General Public License for more details.\n\nYou should have received <doclink href=Copying>a copy of the GNU General Public License</doclink> along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA, or [http://www.gnu.org/copyleft/gpl.html read it online].",
+       "config-sidebar": "* [https://www.mediawiki.org MediaWiki home]\n* [https://www.mediawiki.org/wiki/Special:MyLanguage/Help:Contents User's Guide]\n* [https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Contents Administrator's Guide]\n* [https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:FAQ FAQ]\n----\n* <doclink href=Readme>Read me</doclink>\n* <doclink href=ReleaseNotes>Release notes</doclink>\n* <doclink href=Copying>Copying</doclink>\n* <doclink href=UpgradeDoc>Upgrading</doclink>",
+       "config-env-good": "The environment has been checked.\nYou can install MediaWiki.",
+       "config-env-bad": "The environment has been checked.\nYou cannot install MediaWiki.",
+       "config-env-php": "PHP $1 is installed.",
+       "config-env-hhvm": "HHVM $1 स्थापना गरिएको छ ।",
+       "config-unicode-using-intl": "Using the [http://pecl.php.net/intl intl PECL extension] for Unicode normalization.",
+       "config-unicode-pure-php-warning": "<strong>Warning:</strong> The [http://pecl.php.net/intl intl PECL extension] is not available to handle Unicode normalization, falling back to slow pure-PHP implementation.\nIf you run a high-traffic site, you should read a little on [https://www.mediawiki.org/wiki/Special:MyLanguage/Unicode_normalization_considerations Unicode normalization]."
+}
index a215374..50c0ec0 100644 (file)
@@ -59,6 +59,7 @@
        "config-admin-password-confirm": "Retajpu pasvorton:",
        "config-admin-name-blank": "Enigu salutnomon de administranto.",
        "config-admin-email": "Retpoŝtadreso:",
+       "config-profile-private": "Privata vikio",
        "mainpagetext": "'''MediaWiki estis sukcese instalita.'''",
        "mainpagedocfooter": "Konsultu la [https://meta.wikimedia.org/wiki/MediaWiki_User%27s_Guide Gvidilon por uzantoj de MediaWiki] por informoj pri uzado de vikia programaro.\n\n==Kiel komenci==\n* [https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Configuration_settings Listo de konfiguraĵoj] (angle)\n* [https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:FAQ MediaWiki Oftaj Demandoj] (angle)\n* [https://lists.wikimedia.org/mailman/listinfo/mediawiki-announce Anonco-dissendolisto pri MediaWiki] (angle)\n* [https://www.mediawiki.org/wiki/Special:MyLanguage/Localisation#Translation_resources Preklad MediaWiki do tvojho jazyka]"
 }
index 1d9a78d..0fc0e9f 100644 (file)
@@ -1,8 +1,9 @@
 {
        "@metadata": {
                "authors": [
-                       "Lionslayer"
+                       "Lionslayer",
+                       "Ninjastrikers"
                ]
        },
-       "mainpagetext": "'''မီဒီယာဝီကီကို အောင်မြင်စွာ သွင်းပြီးပါပြီ။'''"
+       "mainpagetext": "<strong>မီဒီယာဝီကီကို အောင်မြင်စွာ သွင်းပြီးပါပြီ။</strong>"
 }
index e1931dd..20ebf9b 100644 (file)
        "config-subscribe-help": "Detta är en e-postlista med låg volym vilken används för meddelanden om nya versionssläpp, inklusive viktiga säkerhetsmeddelanden.\nDu bör prenumerera på den och uppdatera din MediaWiki-installation när nya versioner kommer ut.",
        "config-subscribe-noemail": "Du försökte att prenumerera på e-postlistan för versionssläppsmeddelanden utan att tillhandahålla en e-postadress.\nAnge en e-postadress om du vill prenumerera på e-postlistan.",
        "config-pingback": "Dela data om denna installation med MediaWikis utvecklare.",
+       "config-pingback-help": "Om du väljer det här alternativet kommer MediaWiki periodvis pinga https://www.mediawiki.org med grundläggande data om den här MediaWiki-instansen. Denna data innehåller exempelvis typen av system, PHP-version och valde databas. Wikimedia Foundation delar denna data med MediaWiki-utvecklare för att hjälpa till att guida framtida utvecklingsarbete. Följande data kommer att skickas till ditt system: <pre>$1</pre>",
        "config-almost-done": "Du är nästan färdig!\nDu kan nu hoppa över återstående konfigurationer och installera wikin direkt.",
        "config-optional-continue": "Ställ fler frågor till mig.",
        "config-optional-skip": "Jag är redan uttråkad, bara installera wiki.",
index 98d7d12..a132dc5 100644 (file)
@@ -534,7 +534,7 @@ class JobRunner implements LoggerAwareInterface {
                wfGetLBFactory()->forEachLB( function( LoadBalancer $lb ) use ( $fname ) {
                        $lb->forEachOpenConnection( function( IDatabase $conn ) use ( $fname ) {
                                if ( $conn->writesOrCallbacksPending() ) {
-                                       $conn->query( "SELECT 1", $fname );
+                                       $conn->ping();
                                }
                        } );
                } );
index 25a5a26..5472e83 100644 (file)
@@ -372,6 +372,20 @@ abstract class BagOStuff implements IExpiringStore, LoggerAwareInterface {
                return $success;
        }
 
+       /**
+        * Reset the TTL on a key if it exists
+        *
+        * @param string $key
+        * @param int $expiry
+        * @return bool Success Returns false if there is no key
+        * @since 1.28
+        */
+       public function changeTTL( $key, $expiry = 0 ) {
+               $value = $this->get( $key );
+
+               return ( $value === false ) ? false : $this->set( $key, $value, $expiry );
+       }
+
        /**
         * Acquire an advisory lock on a key string
         *
index ba8c736..5967441 100644 (file)
@@ -79,6 +79,11 @@ class MemcachedBagOStuff extends BagOStuff {
                return $this->mergeViaCas( $key, $callback, $exptime, $attempts );
        }
 
+       public function changeTTL( $key, $exptime = 0 ) {
+               return $this->client->touch( $this->validateKeyEncoding( $key ),
+                       $this->fixExpiry( $exptime ) );
+       }
+
        /**
         * Get the underlying client object. This is provided for debugging
         * purposes.
index 668135d..c3fcab9 100644 (file)
@@ -360,6 +360,48 @@ class MemcachedClient {
                return false;
        }
 
+       /**
+        * Changes the TTL on a key from the server to $time
+        *
+        * @param string $key Key
+        * @param int $time TTL in seconds
+        *
+        * @return bool True on success, false on failure
+        */
+       public function touch( $key, $time = 0 ) {
+               if ( !$this->_active ) {
+                       return false;
+               }
+
+               $sock = $this->get_sock( $key );
+               if ( !is_resource( $sock ) ) {
+                       return false;
+               }
+
+               $key = is_array( $key ) ? $key[1] : $key;
+
+               if ( isset( $this->stats['touch'] ) ) {
+                       $this->stats['touch']++;
+               } else {
+                       $this->stats['touch'] = 1;
+               }
+               $cmd = "touch $key $time\r\n";
+               if ( !$this->_fwrite( $sock, $cmd ) ) {
+                       return false;
+               }
+               $res = $this->_fgets( $sock );
+
+               if ( $this->_debug ) {
+                       $this->_debugprint( sprintf( "MemCache: touch %s (%s)", $key, $res ) );
+               }
+
+               if ( $res == "TOUCHED" ) {
+                       return true;
+               }
+
+               return false;
+       }
+
        /**
         * @param string $key
         * @param int $timeout
index 4fd40e2..143042c 100644 (file)
@@ -466,7 +466,7 @@ class WANObjectCache implements IExpiringStore, LoggerAwareInterface {
         *
         * Example usage:
         * @code
-        *     $dbw->begin( __METHOD__ ); // start of request
+        *     $dbw->startAtomic( __METHOD__ ); // start of request
         *     ... <execute some stuff> ...
         *     // Update the row in the DB
         *     $dbw->update( ... );
@@ -476,7 +476,7 @@ class WANObjectCache implements IExpiringStore, LoggerAwareInterface {
         *         $cache->delete( $key );
         *     } );
         *     ... <execute some stuff> ...
-        *     $dbw->commit( __METHOD__ ); // end of request
+        *     $dbw->endAtomic( __METHOD__ ); // end of request
         * @endcode
         *
         * The $ttl parameter can be used when purging values that have not actually changed
@@ -689,7 +689,9 @@ class WANObjectCache implements IExpiringStore, LoggerAwareInterface {
         *             // Calling touchCheckKey() on this key invalidates the cache
         *             'checkKeys' => [ $cache->makeKey( 'site-cat-config' ) ],
         *             // Try to only let one datacenter thread manage cache updates at a time
-        *             'lockTSE' => 30
+        *             'lockTSE' => 30,
+        *             // Avoid querying cache servers multiple times in a web request
+        *             'pcTTL' => $cache::TTL_PROC_LONG
         *         ]
         *     );
         * @endcode
@@ -743,8 +745,12 @@ class WANObjectCache implements IExpiringStore, LoggerAwareInterface {
         *             // Merge them and get the new "last 100" rows
         *             return array_slice( array_merge( $new, $list ), 0, 100 );
         *        },
-        *        // Try to only let one datacenter thread manage cache updates at a time
-        *        [ 'lockTSE' => 30 ]
+        *        [
+        *             // Try to only let one datacenter thread manage cache updates at a time
+        *             'lockTSE' => 30,
+        *             // Use a magic value when no cache value is ready rather than stampeding
+        *             'busyValue' => 'computing'
+        *        ]
         *     );
         * @endcode
         *
index 16740d8..ed361eb 100644 (file)
@@ -84,11 +84,9 @@ class DjVuImage {
        function dump() {
                $file = fopen( $this->mFilename, 'rb' );
                $header = fread( $file, 12 );
-               // @todo FIXME: Would be good to replace this extract() call with
-               // something that explicitly initializes local variables.
-               extract( unpack( 'a4magic/a4chunk/NchunkLength', $header ) );
-               /** @var string $chunk
-                * @var string $chunkLength */
+               $arr = unpack( 'a4magic/a4chunk/NchunkLength', $header );
+               $chunk = $arr['chunk'];
+               $chunkLength = $arr['chunkLength'];
                echo "$chunk $chunkLength\n";
                $this->dumpForm( $file, $chunkLength, 1 );
                fclose( $file );
@@ -103,11 +101,9 @@ class DjVuImage {
                        if ( $chunkHeader == '' ) {
                                break;
                        }
-                       // @todo FIXME: Would be good to replace this extract() call with
-                       // something that explicitly initializes local variables.
-                       extract( unpack( 'a4chunk/NchunkLength', $chunkHeader ) );
-                       /** @var string $chunk
-                        * @var string $chunkLength */
+                       $arr = unpack( 'a4chunk/NchunkLength', $chunkHeader );
+                       $chunk = $arr['chunk'];
+                       $chunkLength = $arr['chunkLength'];
                        echo str_repeat( ' ', $indent * 4 ) . "$chunk $chunkLength\n";
 
                        if ( $chunk == 'FORM' ) {
@@ -138,24 +134,19 @@ class DjVuImage {
                if ( strlen( $header ) < 16 ) {
                        wfDebug( __METHOD__ . ": too short file header\n" );
                } else {
-                       // @todo FIXME: Would be good to replace this extract() call with
-                       // something that explicitly initializes local variables.
-                       extract( unpack( 'a4magic/a4form/NformLength/a4subtype', $header ) );
-
-                       /** @var string $magic
-                        * @var string $subtype
-                        * @var string $formLength
-                        * @var string $formType */
-                       if ( $magic != 'AT&T' ) {
+                       $arr = unpack( 'a4magic/a4form/NformLength/a4subtype', $header );
+
+                       $subtype = $arr['subtype'];
+                       if ( $arr['magic'] != 'AT&T' ) {
                                wfDebug( __METHOD__ . ": not a DjVu file\n" );
                        } elseif ( $subtype == 'DJVU' ) {
                                // Single-page document
                                $info = $this->getPageInfo( $file );
                        } elseif ( $subtype == 'DJVM' ) {
                                // Multi-page document
-                               $info = $this->getMultiPageInfo( $file, $formLength );
+                               $info = $this->getMultiPageInfo( $file, $arr['formLength'] );
                        } else {
-                               wfDebug( __METHOD__ . ": unrecognized DJVU file type '$formType'\n" );
+                               wfDebug( __METHOD__ . ": unrecognized DJVU file type '{$arr['subtype']}'\n" );
                        }
                }
                fclose( $file );
@@ -168,13 +159,9 @@ class DjVuImage {
                if ( strlen( $header ) < 8 ) {
                        return [ false, 0 ];
                } else {
-                       // @todo FIXME: Would be good to replace this extract() call with
-                       // something that explicitly initializes local variables.
-                       extract( unpack( 'a4chunk/Nlength', $header ) );
+                       $arr = unpack( 'a4chunk/Nlength', $header );
 
-                       /** @var string $chunk
-                        * @var string $length */
-                       return [ $chunk, $length ];
+                       return [ $arr['chunk'], $arr['length'] ];
                }
        }
 
@@ -236,31 +223,22 @@ class DjVuImage {
                        return false;
                }
 
-               // @todo FIXME: Would be good to replace this extract() call with
-               // something that explicitly initializes local variables.
-               extract( unpack(
+               $arr = unpack(
                        'nwidth/' .
                        'nheight/' .
                        'Cminor/' .
                        'Cmajor/' .
                        'vresolution/' .
-                       'Cgamma', $data ) );
+                       'Cgamma', $data );
 
                # Newer files have rotation info in byte 10, but we don't use it yet.
 
-               /** @var string $width
-                * @var string $height
-                * @var string $major
-                * @var string $minor
-                * @var string $resolution
-                * @var string $length
-                * @var string $gamma */
                return [
-                       'width' => $width,
-                       'height' => $height,
-                       'version' => "$major.$minor",
-                       'resolution' => $resolution,
-                       'gamma' => $gamma / 10.0 ];
+                       'width' => $arr['width'],
+                       'height' => $arr['height'],
+                       'version' => "{$arr['major']}.{$arr['minor']}",
+                       'resolution' => $arr['resolution'],
+                       'gamma' => $arr['gamma'] / 10.0 ];
        }
 
        /**
index 090ace8..bb760bd 100644 (file)
@@ -226,4 +226,10 @@ class MemcachedPeclBagOStuff extends MemcachedBagOStuff {
                $result = $this->client->setMulti( $data, $this->fixExpiry( $exptime ) );
                return $this->checkResult( false, $result );
        }
+
+       public function changeTTL( $key, $expiry = 0 ) {
+               $this->debugLog( "touch($key)" );
+               $result = $this->client->touch( $key, $expiry );
+               return $this->checkResult( $key, $result );
+       }
 }
index 1083393..bcdf62f 100644 (file)
@@ -249,7 +249,7 @@ class ObjectCache {
         *     ObjectCache::getLocalServerInstance( $fallbackType );
         *
         *     // From $wgObjectCaches via newFromParams()
-        *     ObjectCache::getLocalServerInstance( array( 'fallback' => $fallbackType ) );
+        *     ObjectCache::getLocalServerInstance( [ 'fallback' => $fallbackType ] );
         *
         * @param int|string|array $fallback Fallback cache or parameter map with 'fallback'
         * @return BagOStuff
index 90508da..c3e0c96 100644 (file)
@@ -272,10 +272,10 @@ class RedisBagOStuff extends BagOStuff {
                if ( !$conn ) {
                        return false;
                }
-               if ( !$conn->exists( $key ) ) {
-                       return null;
-               }
                try {
+                       if ( !$conn->exists( $key ) ) {
+                               return null;
+                       }
                        // @FIXME: on races, the key may have a 0 TTL
                        $result = $conn->incrBy( $key, $value );
                } catch ( RedisException $e ) {
@@ -287,6 +287,24 @@ class RedisBagOStuff extends BagOStuff {
                return $result;
        }
 
+       public function changeTTL( $key, $expiry = 0 ) {
+               list( $server, $conn ) = $this->getConnection( $key );
+               if ( !$conn ) {
+                       return false;
+               }
+
+               $expiry = $this->convertToRelative( $expiry );
+               try {
+                       $result = $conn->expire( $key, $expiry );
+               } catch ( RedisException $e ) {
+                       $result = false;
+                       $this->handleException( $conn, $e );
+               }
+
+               $this->logRequest( 'expire', $key, $server, $result );
+               return $result;
+       }
+
        public function modifySimpleRelayEvent( array $event ) {
                if ( array_key_exists( 'val', $event ) ) {
                        $event['val'] = serialize( $event['val'] ); // this class uses PHP serialization
index f5a860e..6396aaa 100644 (file)
@@ -1196,7 +1196,6 @@ class Article implements Page {
                $token = $user->getEditToken( $rcid );
 
                $outputPage->preventClickjacking();
-               $outputPage->addModuleStyles( 'mediawiki.page.patrol' );
                if ( $wgEnableAPI && $wgEnableWriteAPI && $user->isAllowed( 'writeapi' ) ) {
                        $outputPage->addModules( 'mediawiki.page.patrol.ajax' );
                }
index bded84d..8eba1cc 100644 (file)
@@ -1144,7 +1144,9 @@ class WikiPage implements Page, IDBAccessObject {
         * @param IDatabase $dbw
         * @param int|null $pageId Custom page ID that will be used for the insert statement
         *
-        * @return bool|int The newly created page_id key; false if the title already existed
+        * @return bool|int The newly created page_id key; false if the row was not
+        *   inserted, e.g. because the title already existed or because the specified
+        *   page ID is already in use.
         */
        public function insertOn( $dbw, $pageId = null ) {
                $pageIdForInsert = $pageId ?: $dbw->nextSequenceValue( 'page_page_id_seq' );
index 393644f..a96ca87 100644 (file)
@@ -700,8 +700,8 @@ abstract class IndexPager extends ContextSource implements Pager {
         * not be used in the pager offset or in any links for users.
         *
         * If getIndexField() returns an array of 'querykey' => 'indexfield' pairs then
-        * this must return a corresponding array of 'querykey' => array( fields...) pairs
-        * in order for a request with &count=querykey to use array( fields...) to sort.
+        * this must return a corresponding array of 'querykey' => [ fields... ] pairs
+        * in order for a request with &count=querykey to use [ fields... ] to sort.
         *
         * This is useful for pagers that GROUP BY a unique column (say page_id)
         * and ORDER BY another (say page_len). Using GROUP BY and ORDER BY both on
index f9eea48..206ad00 100644 (file)
@@ -251,7 +251,7 @@ class Parser {
        protected $mProfiler;
 
        /**
-        * @var LinkRenderer
+        * @var \MediaWiki\Linker\LinkRenderer
         */
        protected $mLinkRenderer;
 
@@ -882,10 +882,10 @@ class Parser {
        }
 
        /**
-        * Get a LinkRenderer instance to make links with
+        * Get a \MediaWiki\Linker\LinkRenderer instance to make links with
         *
         * @since 1.28
-        * @return LinkRenderer
+        * @return \MediaWiki\Linker\LinkRenderer
         */
        public function getLinkRenderer() {
                if ( !$this->mLinkRenderer ) {
index 1db9ce5..418d17f 100644 (file)
@@ -121,7 +121,7 @@ class DerivativeResourceLoaderContext extends ResourceLoaderContext {
        }
 
        /**
-        * @param string $user
+        * @param string|null $user
         */
        public function setUser( $user ) {
                $this->user = $user;
index 85a6954..6426fea 100644 (file)
@@ -60,13 +60,13 @@ class ResourceLoader implements LoggerAwareInterface {
 
        /**
         * Associative array mapping framework ids to a list of names of test suite modules
-        * like array( 'qunit' => array( 'mediawiki.tests.qunit.suites', 'ext.foo.tests', .. ), .. )
+        * like [ 'qunit' => [ 'mediawiki.tests.qunit.suites', 'ext.foo.tests', ... ], ... ]
         * @var array
         */
        protected $testModuleNames = [];
 
        /**
-        * E.g. array( 'source-id' => 'http://.../load.php' )
+        * E.g. [ 'source-id' => 'http://.../load.php' ]
         * @var array
         */
        protected $sources = [];
@@ -241,7 +241,7 @@ class ResourceLoader implements LoggerAwareInterface {
                $this->config = $config;
 
                // Add 'local' source first
-               $this->addSource( 'local', wfScript( 'load' ) );
+               $this->addSource( 'local', $config->get( 'LoadScript' ) );
 
                // Add other sources
                $this->addSource( $config->get( 'ResourceLoaderSources' ) );
@@ -433,7 +433,7 @@ class ResourceLoader implements LoggerAwareInterface {
         *
         * Source IDs are typically the same as the Wiki ID or database name (e.g. lowercase a-z).
         *
-        * @param array|string $id Source ID (string), or array( id1 => loadUrl, id2 => loadUrl, ... )
+        * @param array|string $id Source ID (string), or [ id1 => loadUrl, id2 => loadUrl, ... ]
         * @param string|array $loadUrl load.php url (string), or array with loadUrl key for
         *  backwards-compatibility.
         * @throws MWException
@@ -573,7 +573,7 @@ class ResourceLoader implements LoggerAwareInterface {
        /**
         * Get the list of sources.
         *
-        * @return array Like array( id => load.php url, .. )
+        * @return array Like [ id => load.php url, ... ]
         */
        public function getSources() {
                return $this->sources;
@@ -1173,7 +1173,7 @@ MESSAGE;
         *    - ResourceLoader::makeLoaderStateScript( $name, $state ):
         *         Set the state of a single module called $name to $state
         *
-        *    - ResourceLoader::makeLoaderStateScript( array( $name => $state, ... ) ):
+        *    - ResourceLoader::makeLoaderStateScript( [ $name => $state, ... ] ):
         *         Set the state of modules with the given names to the given states
         *
         * @param string $name
@@ -1264,14 +1264,14 @@ MESSAGE;
         *     ):
         *        Register a single module.
         *
-        *   - ResourceLoader::makeLoaderRegisterScript( array( $name1, $name2 ) ):
+        *   - ResourceLoader::makeLoaderRegisterScript( [ $name1, $name2 ] ):
         *        Register modules with the given names.
         *
-        *   - ResourceLoader::makeLoaderRegisterScript( array(
-        *        array( $name1, $version1, $dependencies1, $group1, $source1, $skip1 ),
-        *        array( $name2, $version2, $dependencies1, $group2, $source2, $skip2 ),
+        *   - ResourceLoader::makeLoaderRegisterScript( [
+        *        [ $name1, $version1, $dependencies1, $group1, $source1, $skip1 ],
+        *        [ $name2, $version2, $dependencies1, $group2, $source2, $skip2 ],
         *        ...
-        *     ) ):
+        *     ] ):
         *        Registers modules with the given names and parameters.
         *
         * @param string $name Module name
@@ -1329,7 +1329,7 @@ MESSAGE;
         *   - ResourceLoader::makeLoaderSourcesScript( $id, $properties ):
         *       Register a single source
         *
-        *   - ResourceLoader::makeLoaderSourcesScript( array( $id1 => $loadUrl, $id2 => $loadUrl, ... ) );
+        *   - ResourceLoader::makeLoaderSourcesScript( [ $id1 => $loadUrl, $id2 => $loadUrl, ... ] );
         *       Register sources with the given IDs and properties.
         *
         * @param string $id Source ID
@@ -1402,13 +1402,13 @@ MESSAGE;
        /**
         * Convert an array of module names to a packed query string.
         *
-        * For example, array( 'foo.bar', 'foo.baz', 'bar.baz', 'bar.quux' )
+        * For example, [ 'foo.bar', 'foo.baz', 'bar.baz', 'bar.quux' ]
         * becomes 'foo.bar,baz|bar.baz,quux'
         * @param array $modules List of module names (strings)
         * @return string Packed query string
         */
        public static function makePackedModulesString( $modules ) {
-               $groups = []; // array( prefix => array( suffixes ) )
+               $groups = []; // [ prefix => [ suffixes ] ]
                foreach ( $modules as $module ) {
                        $pos = strrpos( $module, '.' );
                        $prefix = $pos === false ? '' : substr( $module, 0, $pos );
diff --git a/includes/resourceloader/ResourceLoaderClientHtml.php b/includes/resourceloader/ResourceLoaderClientHtml.php
new file mode 100644 (file)
index 0000000..3093cde
--- /dev/null
@@ -0,0 +1,482 @@
+<?php
+/**
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * http://www.gnu.org/copyleft/gpl.html
+ *
+ * @file
+ */
+
+use WrappedString\WrappedStringList;
+
+/**
+ * Bootstrap a ResourceLoader client on an HTML page.
+ *
+ * @since 1.28
+ */
+class ResourceLoaderClientHtml {
+
+       /** @var ResourceLoaderContext */
+       private $context;
+
+       /** @var ResourceLoader */
+       private $resourceLoader;
+
+       /** @var array */
+       private $config = [];
+
+       /** @var array */
+       private $modules = [];
+
+       /** @var array */
+       private $moduleStyles = [];
+
+       /** @var array */
+       private $moduleScripts = [];
+
+       /** @var array */
+       private $exemptStates = [];
+
+       /** @var array */
+       private $data;
+
+       /**
+        * @param ResourceLoaderContext $context
+        */
+       public function __construct( ResourceLoaderContext $context ) {
+               $this->context = $context;
+               $this->resourceLoader = $context->getResourceLoader();
+       }
+
+       /**
+        * Set mw.config variables.
+        *
+        * @param array $vars Array of key/value pairs
+        */
+       public function setConfig( array $vars ) {
+               foreach ( $vars as $key => $value ) {
+                       $this->config[$key] = $value;
+               }
+       }
+
+       /**
+        * Ensure one or more modules are loaded.
+        *
+        * @param array $modules Array of module names
+        */
+       public function setModules( array $modules ) {
+               $this->modules = $modules;
+       }
+
+       /**
+        * Ensure the styles of one or more modules are loaded.
+        *
+        * @deprecated since 1.28
+        * @param array $modules Array of module names
+        */
+       public function setModuleStyles( array $modules ) {
+               $this->moduleStyles = $modules;
+       }
+
+       /**
+        * Ensure the scripts of one or more modules are loaded.
+        *
+        * @deprecated since 1.28
+        * @param array $modules Array of module names
+        */
+       public function setModuleScripts( array $modules ) {
+               $this->moduleScripts = $modules;
+       }
+
+       /**
+        * Set state of special modules that are handled by the caller manually.
+        *
+        * See OutputPage::buildExemptModules() for use cases.
+        *
+        * @param array $modules Module state keyed by module name
+        */
+       public function setExemptStates( array $states ) {
+               $this->exemptStates = $states;
+       }
+
+       /**
+        * @return array
+        */
+       private function getData() {
+               if ( $this->data ) {
+                       // @codeCoverageIgnoreStart
+                       return $this->data;
+                       // @codeCoverageIgnoreEnd
+               }
+
+               $rl = $this->resourceLoader;
+               $data = [
+                       'states' => [
+                               // moduleName => state
+                       ],
+                       'general' => [
+                               // position => [ moduleName ]
+                               'top' => [],
+                               'bottom' => [],
+                       ],
+                       'styles' => [
+                               // moduleName
+                       ],
+                       'scripts' => [
+                               // position => [ moduleName ]
+                               'top' => [],
+                               'bottom' => [],
+                       ],
+                       // Embedding for private modules
+                       'embed' => [
+                               'styles' => [],
+                               'general' => [
+                                       'top' => [],
+                                       'bottom' => [],
+                               ],
+                       ],
+
+               ];
+
+               foreach ( $this->modules as $name ) {
+                       $module = $rl->getModule( $name );
+                       if ( !$module ) {
+                               continue;
+                       }
+
+                       $group = $module->getGroup();
+                       $position = $module->getPosition();
+
+                       if ( $group === 'private' ) {
+                               // Embed via mw.loader.implement per T36907.
+                               $data['embed']['general'][$position][] = $name;
+                               // Avoid duplicate request from mw.loader
+                               $data['states'][$name] = 'loading';
+                       } else {
+                               // Load via mw.loader.load()
+                               $data['general'][$position][] = $name;
+                       }
+               }
+
+               foreach ( $this->moduleStyles as $name ) {
+                       $module = $rl->getModule( $name );
+                       if ( !$module ) {
+                               continue;
+                       }
+
+                       if ( $module->getType() !== ResourceLoaderModule::LOAD_STYLES ) {
+                               $logger = $rl->getLogger();
+                               $logger->debug( 'Unexpected general module "{module}" in styles queue.', [
+                                       'module' => $name,
+                               ] );
+                       } else {
+                               // Stylesheet doesn't trigger mw.loader callback.
+                               // Set "ready" state to allow dependencies and avoid duplicate requests. (T87871)
+                               $data['states'][$name] = 'ready';
+                       }
+
+                       $group = $module->getGroup();
+                       $context = $this->getContext( $group, ResourceLoaderModule::TYPE_STYLES );
+                       if ( $module->isKnownEmpty( $context ) ) {
+                               // Avoid needless request for empty module
+                               $data['states'][$name] = 'ready';
+                       } else {
+                               if ( $group === 'private' ) {
+                                       // Embed via style element
+                                       $data['embed']['styles'][] = $name;
+                                       // Avoid duplicate request from mw.loader
+                                       $data['states'][$name] = 'ready';
+                               } else {
+                                       // Load from load.php?only=styles via <link rel=stylesheet>
+                                       $data['styles'][] = $name;
+                               }
+                       }
+               }
+
+               foreach ( $this->moduleScripts as $name ) {
+                       $module = $rl->getModule( $name );
+                       if ( !$module ) {
+                               continue;
+                       }
+
+                       $group = $module->getGroup();
+                       $position = $module->getPosition();
+                       $context = $this->getContext( $group, ResourceLoaderModule::TYPE_SCRIPTS );
+                       if ( $module->isKnownEmpty( $context ) ) {
+                               // Avoid needless request for empty module
+                               $data['states'][$name] = 'ready';
+                       } else {
+                               // Load from load.php?only=scripts via <script src></script>
+                               $data['scripts'][$position][] = $name;
+
+                               // Avoid duplicate request from mw.loader
+                               $data['states'][$name] = 'loading';
+                       }
+               }
+
+               return $data;
+       }
+
+       /**
+        * @return array Attribute key-value pairs for the HTML document element
+        */
+       public function getDocumentAttributes() {
+               return [ 'class' => 'client-nojs' ];
+       }
+
+       /**
+        * The order of elements in the head is as follows:
+        * - Inline scripts.
+        * - Stylesheets.
+        * - Async external script-src.
+        *
+        * Reasons:
+        * - Script execution may be blocked on preceeding stylesheets.
+        * - Async scripts are not blocked on stylesheets.
+        * - Inline scripts can't be asynchronous.
+        * - For styles, earlier is better.
+        *
+        * @return string|WrappedStringList HTML
+        */
+       public function getHeadHtml() {
+               $data = $this->getData();
+               $chunks = [];
+
+               // Change "client-nojs" class to client-js. This allows easy toggling of UI components.
+               // This happens synchronously on every page view to avoid flashes of wrong content.
+               // See also #getDocumentAttributes() and /resources/src/startup.js.
+               $chunks[] = Html::inlineScript(
+                       'document.documentElement.className = document.documentElement.className'
+                       . '.replace( /(^|\s)client-nojs(\s|$)/, "$1client-js$2" );'
+               );
+
+               // Inline RLQ: Set page variables
+               if ( $this->config ) {
+                       $chunks[] = ResourceLoader::makeInlineScript(
+                               ResourceLoader::makeConfigSetScript( $this->config )
+                       );
+               }
+
+               // Inline RLQ: Initial module states
+               $states = array_merge( $this->exemptStates, $data['states'] );
+               if ( $states ) {
+                       $chunks[] = ResourceLoader::makeInlineScript(
+                               ResourceLoader::makeLoaderStateScript( $states )
+                       );
+               }
+
+               // Inline RLQ: Embedded modules
+               if ( $data['embed']['general']['top'] ) {
+                       $chunks[] = $this->getLoad(
+                               $data['embed']['general']['top'],
+                               ResourceLoaderModule::TYPE_COMBINED
+                       );
+               }
+
+               // Inline RLQ: Load general modules
+               if ( $data['general']['top'] ) {
+                       $chunks[] = ResourceLoader::makeInlineScript(
+                               Xml::encodeJsCall( 'mw.loader.load', [ $data['general']['top'] ] )
+                       );
+               }
+
+               // Inline RLQ: Load only=scripts
+               if ( $data['scripts']['top'] ) {
+                       $chunks[] = $this->getLoad(
+                               $data['scripts']['top'],
+                               ResourceLoaderModule::TYPE_SCRIPTS
+                       );
+               }
+
+               // External stylesheets
+               if ( $data['styles'] ) {
+                       $chunks[] = $this->getLoad(
+                               $data['styles'],
+                               ResourceLoaderModule::TYPE_STYLES
+                       );
+               }
+
+               // Inline stylesheets (embedded only=styles)
+               if ( $data['embed']['styles'] ) {
+                       $chunks[] = $this->getLoad(
+                               $data['embed']['styles'],
+                               ResourceLoaderModule::TYPE_STYLES
+                       );
+               }
+
+               // Async scripts. Once the startup is loaded, inline RLQ scripts will run.
+               $chunks[] = $this->getLoad( 'startup', ResourceLoaderModule::TYPE_SCRIPTS );
+
+               return WrappedStringList::join( "\n", $chunks );
+       }
+
+       /**
+        * @return string|WrappedStringList HTML
+        */
+       public function getBodyHtml() {
+               $data = $this->getData();
+               $chunks = [];
+
+               // Inline RLQ: Embedded modules
+               if ( $data['embed']['general']['bottom'] ) {
+                       $chunks[] = $this->getLoad(
+                               $data['embed']['general']['bottom'],
+                               ResourceLoaderModule::TYPE_COMBINED
+                       );
+               }
+
+               // Inline RLQ: Load only=scripts
+               if ( $data['scripts']['bottom'] ) {
+                       $chunks[] = $this->getLoad(
+                               $data['scripts']['bottom'],
+                               ResourceLoaderModule::TYPE_SCRIPTS
+                       );
+               }
+
+               // Inline RLQ: Load general modules
+               if ( $data['general']['bottom'] ) {
+                       $chunks[] = ResourceLoader::makeInlineScript(
+                               Xml::encodeJsCall( 'mw.loader.load', [ $data['general']['bottom'] ] )
+                       );
+               }
+
+               return WrappedStringList::join( "\n", $chunks );
+       }
+
+       private function getContext( $group, $type ) {
+               return self::makeContext( $this->context, $group, $type );
+       }
+
+       private function getLoad( $modules, $only ) {
+               return self::makeLoad( $this->context, (array)$modules, $only );
+       }
+
+       private static function makeContext( ResourceLoaderContext $mainContext, $group, $type,
+               array $extraQuery = []
+       ) {
+               // Create new ResourceLoaderContext so that $extraQuery may trigger isRaw().
+               $req = new FauxRequest( array_merge( $mainContext->getRequest()->getValues(), $extraQuery ) );
+               // Set 'only' if not combined
+               $req->setVal( 'only', $type === ResourceLoaderModule::TYPE_COMBINED ? null : $type );
+               // Remove user parameter in most cases
+               if ( $group !== 'user' && $group !== 'private' ) {
+                       $req->setVal( 'user', null );
+               }
+               $context = new ResourceLoaderContext( $mainContext->getResourceLoader(), $req );
+               // Allow caller to setVersion() and setModules()
+               return new DerivativeResourceLoaderContext( $context );
+       }
+
+       /**
+        * Explicily load or embed modules on a page.
+        *
+        * @param ResourceLoaderContext $mainContext
+        * @param array $modules One or more module names
+        * @param string $only ResourceLoaderModule TYPE_ class constant
+        * @param array $extraQuery [optional] Array with extra query parameters for the request
+        * @return string|WrappedStringList HTML
+        */
+       public static function makeLoad( ResourceLoaderContext $mainContext, array $modules, $only,
+               array $extraQuery = []
+       ) {
+               $rl = $mainContext->getResourceLoader();
+               $chunks = [];
+
+               if ( $mainContext->getDebug() && count( $modules ) > 1 ) {
+                       $chunks = [];
+                       // Recursively call us for every item
+                       foreach ( $modules as $name ) {
+                               $chunks[] = self::makeLoad( $mainContext, [ $name ], $only, $extraQuery );
+                       }
+                       return new WrappedStringList( "\n", $chunks );
+               }
+
+               // Sort module names so requests are more uniform
+               sort( $modules );
+               // Create keyed-by-source and then keyed-by-group list of module objects from modules list
+               $sortedModules = [];
+               foreach ( $modules as $name ) {
+                       $module = $rl->getModule( $name );
+                       if ( !$module ) {
+                               $rl->getLogger()->warning( 'Unknown module "{module}"', [ 'module' => $name ] );
+                               continue;
+                       }
+                       $sortedModules[$module->getSource()][$module->getGroup()][$name] = $module;
+               }
+
+               foreach ( $sortedModules as $source => $groups ) {
+                       foreach ( $groups as $group => $grpModules ) {
+                               $context = self::makeContext( $mainContext, $group, $only, $extraQuery );
+
+                               if ( $group === 'private' ) {
+                                       // Decide whether to use style or script element
+                                       if ( $only == ResourceLoaderModule::TYPE_STYLES ) {
+                                               $chunks[] = Html::inlineStyle(
+                                                       $rl->makeModuleResponse( $context, $grpModules )
+                                               );
+                                       } else {
+                                               $chunks[] = ResourceLoader::makeInlineScript(
+                                                       $rl->makeModuleResponse( $context, $grpModules )
+                                               );
+                                       }
+                                       continue;
+                               }
+
+                               // See if we have one or more raw modules
+                               $isRaw = false;
+                               foreach ( $grpModules as $key => $module ) {
+                                       $isRaw |= $module->isRaw();
+                               }
+
+                               // Special handling for the user group; because users might change their stuff
+                               // on-wiki like user pages, or user preferences; we need to find the highest
+                               // timestamp of these user-changeable modules so we can ensure cache misses on change
+                               // This should NOT be done for the site group (bug 27564) because anons get that too
+                               // and we shouldn't be putting timestamps in CDN-cached HTML
+                               if ( $group === 'user' ) {
+                                       $version = $rl->getCombinedVersion( $context, array_keys( $grpModules ) );
+                                       $context->setVersion( $version );
+                               }
+
+                               $context->setModules( array_keys( $grpModules ) );
+                               $url = $rl->createLoaderURL( $source, $context, $extraQuery );
+
+                               // Decide whether to use 'style' or 'script' element
+                               if ( $only === ResourceLoaderModule::TYPE_STYLES ) {
+                                       $chunk = Html::linkedStyle( $url );
+                               } else {
+                                       if ( $context->getRaw() || $isRaw ) {
+                                               $chunk = Html::element( 'script', [
+                                                       // In SpecialJavaScriptTest, QUnit must load synchronous
+                                                       'async' => !isset( $extraQuery['sync'] ),
+                                                       'src' => $url
+                                               ] );
+                                       } else {
+                                               $chunk = ResourceLoader::makeInlineScript(
+                                                       Xml::encodeJsCall( 'mw.loader.load', [ $url ] )
+                                               );
+                                       }
+                               }
+
+                               if ( $group == 'noscript' ) {
+                                       $chunks[] = Html::rawElement( 'noscript', [], $chunk );
+                               } else {
+                                       $chunks[] = $chunk;
+                               }
+                       }
+               }
+
+               return new WrappedStringList( "\n", $chunks );
+       }
+}
index 85fc53d..79b71df 100644 (file)
@@ -91,8 +91,8 @@ class ResourceLoaderContext {
 
        /**
         * Expand a string of the form jquery.foo,bar|jquery.ui.baz,quux to
-        * an array of module names like array( 'jquery.foo', 'jquery.bar',
-        * 'jquery.ui.baz', 'jquery.ui.quux' )
+        * an array of module names like [ 'jquery.foo', 'jquery.bar',
+        * 'jquery.ui.baz', 'jquery.ui.quux' ]
         * @param string $modules Packed module name list
         * @return array Array of module names
         */
@@ -113,7 +113,7 @@ class ResourceLoaderContext {
                                } else {
                                        // We have a prefix and a bunch of suffixes
                                        $prefix = substr( $group, 0, $pos ); // 'foo'
-                                       $suffixes = explode( ',', substr( $group, $pos + 1 ) ); // array( 'bar', 'baz' )
+                                       $suffixes = explode( ',', substr( $group, $pos + 1 ) ); // [ 'bar', 'baz' ]
                                        foreach ( $suffixes as $suffix ) {
                                                $retval[] = "$prefix.$suffix";
                                        }
@@ -260,7 +260,7 @@ class ResourceLoaderContext {
 
        /**
         * @see ResourceLoaderModule::getVersionHash
-        * @see OutputPage::makeResourceLoaderLink
+        * @see ResourceLoaderClientHtml::makeLoad
         * @return string|null
         */
        public function getVersion() {
index 2816126..574e535 100644 (file)
@@ -41,7 +41,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         * @var array List of paths to JavaScript files to always include
         * @par Usage:
         * @code
-        * array( [file-path], [file-path], ... )
+        * [ [file-path], [file-path], ... ]
         * @endcode
         */
        protected $scripts = [];
@@ -50,7 +50,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         * @var array List of JavaScript files to include when using a specific language
         * @par Usage:
         * @code
-        * array( [language-code] => array( [file-path], [file-path], ... ), ... )
+        * [ [language-code] => [ [file-path], [file-path], ... ], ... ]
         * @endcode
         */
        protected $languageScripts = [];
@@ -59,7 +59,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         * @var array List of JavaScript files to include when using a specific skin
         * @par Usage:
         * @code
-        * array( [skin-name] => array( [file-path], [file-path], ... ), ... )
+        * [ [skin-name] => [ [file-path], [file-path], ... ], ... ]
         * @endcode
         */
        protected $skinScripts = [];
@@ -68,7 +68,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         * @var array List of paths to JavaScript files to include in debug mode
         * @par Usage:
         * @code
-        * array( [skin-name] => array( [file-path], [file-path], ... ), ... )
+        * [ [skin-name] => [ [file-path], [file-path], ... ], ... ]
         * @endcode
         */
        protected $debugScripts = [];
@@ -77,7 +77,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         * @var array List of paths to CSS files to always include
         * @par Usage:
         * @code
-        * array( [file-path], [file-path], ... )
+        * [ [file-path], [file-path], ... ]
         * @endcode
         */
        protected $styles = [];
@@ -86,7 +86,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         * @var array List of paths to CSS files to include when using specific skins
         * @par Usage:
         * @code
-        * array( [file-path], [file-path], ... )
+        * [ [file-path], [file-path], ... ]
         * @endcode
         */
        protected $skinStyles = [];
@@ -95,7 +95,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         * @var array List of modules this module depends on
         * @par Usage:
         * @code
-        * array( [file-path], [file-path], ... )
+        * [ [file-path], [file-path], ... ]
         * @endcode
         */
        protected $dependencies = [];
@@ -109,7 +109,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         * @var array List of message keys used by this module
         * @par Usage:
         * @code
-        * array( [message-key], [message-key], ... )
+        * [ [message-key], [message-key], ... ]
         * @endcode
         */
        protected $messages = [];
@@ -138,7 +138,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         * @var array Place where readStyleFile() tracks file dependencies
         * @par Usage:
         * @code
-        * array( [file-path], [file-path], ... )
+        * [ [file-path], [file-path], ... ]
         * @endcode
         */
        protected $localFileRefs = [];
@@ -165,7 +165,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         * @throws InvalidArgumentException
         * @par Construction options:
         * @code
-        *     array(
+        *     [
         *         // Base path to prepend to all local paths in $options. Defaults to $IP
         *         'localBasePath' => [base path],
         *         // Base path to prepend to all remote paths in $options. Defaults to $wgResourceBasePath
@@ -207,7 +207,7 @@ class ResourceLoaderFileModule extends ResourceLoaderModule {
         *         // The file must contain valid JavaScript for execution in a private function.
         *         // The file must not contain the "function () {" and "}" wrapper though.
         *         'skipFunction' => [file path]
-        *     )
+        *     ]
         * @endcode
         */
        public function __construct(
index 87e5fd7..2503b22 100644 (file)
@@ -54,8 +54,8 @@ class ResourceLoaderImage {
                $this->variants = $variants;
 
                // Expand shorthands:
-               // array( "en,de,fr" => "foo.svg" )
-               // → array( "en" => "foo.svg", "de" => "foo.svg", "fr" => "foo.svg" )
+               // [ "en,de,fr" => "foo.svg" ]
+               // → [ "en" => "foo.svg", "de" => "foo.svg", "fr" => "foo.svg" ]
                if ( is_array( $this->descriptor ) && isset( $this->descriptor['lang'] ) ) {
                        foreach ( array_keys( $this->descriptor['lang'] ) as $langList ) {
                                if ( strpos( $langList, ',' ) !== false ) {
index b3b3f16..c1b47bf 100644 (file)
@@ -64,6 +64,13 @@ class ResourceLoaderUserOptionsModule extends ResourceLoaderModule {
                return false;
        }
 
+       /**
+        * @return string
+        */
+       public function getPosition() {
+               return 'top';
+       }
+
        /**
         * @return string
         */
index cea1f39..c8a0ff1 100644 (file)
@@ -74,6 +74,13 @@ class ResourceLoaderUserTokensModule extends ResourceLoaderModule {
                return false;
        }
 
+       /**
+        * @return string
+        */
+       public function getPosition() {
+               return 'top';
+       }
+
        /**
         * @return string
         */
index 3e5ef3b..8ccb6d1 100644 (file)
@@ -374,202 +374,15 @@ final class SessionManager implements SessionManagerInterface {
         * @deprecated since 1.27, use MediaWiki\Auth\AuthManager::autoCreateUser instead
         * @param User $user User to auto-create
         * @return bool Success
+        * @codeCoverageIgnore
         */
        public static function autoCreateUser( User $user ) {
-               global $wgAuth, $wgDisableAuthManager;
-
-               // @codeCoverageIgnoreStart
-               if ( !$wgDisableAuthManager ) {
-                       wfDeprecated( __METHOD__, '1.27' );
-                       return \MediaWiki\Auth\AuthManager::singleton()->autoCreateUser(
-                               $user,
-                               \MediaWiki\Auth\AuthManager::AUTOCREATE_SOURCE_SESSION,
-                               false
-                       )->isGood();
-               }
-               // @codeCoverageIgnoreEnd
-
-               $logger = self::singleton()->logger;
-
-               // Much of this code is based on that in CentralAuth
-
-               // Try the local user from the slave DB
-               $localId = User::idFromName( $user->getName() );
-               $flags = 0;
-
-               // Fetch the user ID from the master, so that we don't try to create the user
-               // when they already exist, due to replication lag
-               // @codeCoverageIgnoreStart
-               if ( !$localId && wfGetLB()->getReaderIndex() != 0 ) {
-                       $localId = User::idFromName( $user->getName(), User::READ_LATEST );
-                       $flags = User::READ_LATEST;
-               }
-               // @codeCoverageIgnoreEnd
-
-               if ( $localId ) {
-                       // User exists after all.
-                       $user->setId( $localId );
-                       $user->loadFromId( $flags );
-                       return false;
-               }
-
-               // Denied by AuthPlugin? But ignore AuthPlugin itself.
-               if ( get_class( $wgAuth ) !== 'AuthPlugin' && !$wgAuth->autoCreate() ) {
-                       $logger->debug( __METHOD__ . ': denied by AuthPlugin' );
-                       $user->setId( 0 );
-                       $user->loadFromId();
-                       return false;
-               }
-
-               // Wiki is read-only?
-               if ( wfReadOnly() ) {
-                       $logger->debug( __METHOD__ . ': denied by wfReadOnly()' );
-                       $user->setId( 0 );
-                       $user->loadFromId();
-                       return false;
-               }
-
-               $userName = $user->getName();
-
-               // Check the session, if we tried to create this user already there's
-               // no point in retrying.
-               $session = self::getGlobalSession();
-               $reason = $session->get( 'MWSession::AutoCreateBlacklist' );
-               if ( $reason ) {
-                       $logger->debug( __METHOD__ . ": blacklisted in session ($reason)" );
-                       $user->setId( 0 );
-                       $user->loadFromId();
-                       return false;
-               }
-
-               // Is the IP user able to create accounts?
-               $anon = new User;
-               if ( !$anon->isAllowedAny( 'createaccount', 'autocreateaccount' )
-                       || $anon->isBlockedFromCreateAccount()
-               ) {
-                       // Blacklist the user to avoid repeated DB queries subsequently
-                       $logger->debug( __METHOD__ . ': user is blocked from this wiki, blacklisting' );
-                       $session->set( 'MWSession::AutoCreateBlacklist', 'blocked', 600 );
-                       $session->persist();
-                       $user->setId( 0 );
-                       $user->loadFromId();
-                       return false;
-               }
-
-               // Check for validity of username
-               if ( !User::isCreatableName( $userName ) ) {
-                       $logger->debug( __METHOD__ . ': Invalid username, blacklisting' );
-                       $session->set( 'MWSession::AutoCreateBlacklist', 'invalid username', 600 );
-                       $session->persist();
-                       $user->setId( 0 );
-                       $user->loadFromId();
-                       return false;
-               }
-
-               // Give other extensions a chance to stop auto creation.
-               $user->loadDefaults( $userName );
-               $abortMessage = '';
-               if ( !\Hooks::run( 'AbortAutoAccount', [ $user, &$abortMessage ] ) ) {
-                       // In this case we have no way to return the message to the user,
-                       // but we can log it.
-                       $logger->debug( __METHOD__ . ": denied by hook: $abortMessage" );
-                       $session->set( 'MWSession::AutoCreateBlacklist', "hook aborted: $abortMessage", 600 );
-                       $session->persist();
-                       $user->setId( 0 );
-                       $user->loadFromId();
-                       return false;
-               }
-
-               // Make sure the name has not been changed
-               if ( $user->getName() !== $userName ) {
-                       $user->setId( 0 );
-                       $user->loadFromId();
-                       throw new \UnexpectedValueException(
-                               'AbortAutoAccount hook tried to change the user name'
-                       );
-               }
-
-               // Ignore warnings about master connections/writes...hard to avoid here
-               \Profiler::instance()->getTransactionProfiler()->resetExpectations();
-
-               $cache = \ObjectCache::getLocalClusterInstance();
-               $backoffKey = wfMemcKey( 'MWSession', 'autocreate-failed', md5( $userName ) );
-               if ( $cache->get( $backoffKey ) ) {
-                       $logger->debug( __METHOD__ . ': denied by prior creation attempt failures' );
-                       $user->setId( 0 );
-                       $user->loadFromId();
-                       return false;
-               }
-
-               // Checks passed, create the user...
-               $from = isset( $_SERVER['REQUEST_URI'] ) ? $_SERVER['REQUEST_URI'] : 'CLI';
-               $logger->info( __METHOD__ . ': creating new user ({username}) - from: {url}',
-                       [
-                               'username' => $userName,
-                               'url' => $from,
-               ] );
-
-               try {
-                       // Insert the user into the local DB master
-                       $status = $user->addToDatabase();
-                       if ( !$status->isOK() ) {
-                               // @codeCoverageIgnoreStart
-                               // double-check for a race condition (T70012)
-                               $id = User::idFromName( $user->getName(), User::READ_LATEST );
-                               if ( $id ) {
-                                       $logger->info( __METHOD__ . ': tried to autocreate existing user',
-                                               [
-                                                       'username' => $userName,
-                                               ] );
-                               } else {
-                                       $logger->error(
-                                               __METHOD__ . ': failed with message ' . $status->getWikiText( false, false, 'en' ),
-                                               [
-                                                       'username' => $userName,
-                                               ]
-                                       );
-                               }
-                               $user->setId( $id );
-                               $user->loadFromId( User::READ_LATEST );
-                               return false;
-                               // @codeCoverageIgnoreEnd
-                       }
-               } catch ( \Exception $ex ) {
-                       // @codeCoverageIgnoreStart
-                       $logger->error( __METHOD__ . ': failed with exception {exception}', [
-                               'exception' => $ex,
-                               'username' => $userName,
-                       ] );
-                       // Do not keep throwing errors for a while
-                       $cache->set( $backoffKey, 1, 600 );
-                       // Bubble up error; which should normally trigger DB rollbacks
-                       throw $ex;
-                       // @codeCoverageIgnoreEnd
-               }
-
-               # Notify AuthPlugin
-               // @codeCoverageIgnoreStart
-               $tmpUser = $user;
-               $wgAuth->initUser( $tmpUser, true );
-               if ( $tmpUser !== $user ) {
-                       $logger->warning( __METHOD__ . ': ' .
-                               get_class( $wgAuth ) . '::initUser() replaced the user object' );
-               }
-               // @codeCoverageIgnoreEnd
-
-               # Notify hooks (e.g. Newuserlog)
-               \Hooks::run( 'AuthPluginAutoCreate', [ $user ] );
-               \Hooks::run( 'LocalUserCreated', [ $user, true ] );
-
-               $user->saveSettings();
-
-               # Update user count
-               \DeferredUpdates::addUpdate( new \SiteStatsUpdate( 0, 0, 0, 0, 1 ) );
-
-               # Watch user's userpage and talk page
-               $user->addWatch( $user->getUserPage(), User::IGNORE_USER_RIGHTS );
-
-               return true;
+               wfDeprecated( __METHOD__, '1.27' );
+               return \MediaWiki\Auth\AuthManager::singleton()->autoCreateUser(
+                       $user,
+                       \MediaWiki\Auth\AuthManager::AUTOCREATE_SOURCE_SESSION,
+                       false
+               )->isGood();
        }
 
        /**
index 69e2e8b..749a686 100644 (file)
@@ -456,7 +456,6 @@ class SkinTemplate extends Skin {
                $tpl->set( 'indicators', $out->getIndicators() );
 
                $tpl->set( 'sitenotice', $this->getSiteNotice() );
-               $tpl->set( 'bottomscripts', $this->bottomScripts() );
                $tpl->set( 'printfooter', $this->printSource() );
                // Wrap the bodyText with #mw-content-text element
                $out->mBodytext = $this->wrapHTML( $title, $out->mBodytext );
@@ -509,6 +508,9 @@ class SkinTemplate extends Skin {
                // See Skin::afterContentHook() for further documentation.
                $tpl->set( 'dataAfterContent', $this->afterContentHook() );
 
+               // Do this last in case hooks above add bottom scripts
+               $tpl->set( 'bottomscripts', $this->bottomScripts() );
+
                return $tpl;
        }
 
@@ -665,34 +667,17 @@ class SkinTemplate extends Skin {
                                ? 'nav-login-createaccount'
                                : 'pt-login';
 
-                       // TODO remove this after AuthManager is stable
-                       global $wgDisableAuthManager;
-                       if ( $wgDisableAuthManager ) {
-                               $is_signup = $request->getText( 'type' ) == 'signup';
-                               $login_url = [
-                                       'text' => $this->msg( $loginlink )->text(),
-                                       'href' => self::makeSpecialUrl( 'Userlogin', $returnto ),
-                                       'active' => $title->isSpecial( 'Userlogin' )
-                                               && ( $loginlink == 'nav-login-createaccount' || !$is_signup ),
-                               ];
-                               $createaccount_url = [
-                                       'text' => $this->msg( 'pt-createaccount' )->text(),
-                                       'href' => self::makeSpecialUrl( 'Userlogin', "$returnto&type=signup" ),
-                                       'active' => $title->isSpecial( 'Userlogin' ) && $is_signup,
-                               ];
-                       } else {
-                               $login_url = [
-                                       'text' => $this->msg( $loginlink )->text(),
-                                       'href' => self::makeSpecialUrl( 'Userlogin', $returnto ),
-                                       'active' => $title->isSpecial( 'Userlogin' ) ||
-                                               $title->isSpecial( 'CreateAccount' ) && $useCombinedLoginLink,
-                               ];
-                               $createaccount_url = [
-                                       'text' => $this->msg( 'pt-createaccount' )->text(),
-                                       'href' => self::makeSpecialUrl( 'CreateAccount', $returnto ),
-                                       'active' => $title->isSpecial( 'CreateAccount' ),
-                               ];
-                       }
+                       $login_url = [
+                               'text' => $this->msg( $loginlink )->text(),
+                               'href' => self::makeSpecialUrl( 'Userlogin', $returnto ),
+                               'active' => $title->isSpecial( 'Userlogin' )
+                                       || $title->isSpecial( 'CreateAccount' ) && $useCombinedLoginLink,
+                       ];
+                       $createaccount_url = [
+                               'text' => $this->msg( 'pt-createaccount' )->text(),
+                               'href' => self::makeSpecialUrl( 'CreateAccount', $returnto ),
+                               'active' => $title->isSpecial( 'CreateAccount' ),
+                       ];
 
                        // No need to show Talk and Contributions to anons if they can't contribute!
                        if ( User::groupHasPermission( '*', 'edit' ) ) {
index c889b73..85b8dc3 100644 (file)
@@ -455,7 +455,7 @@ abstract class AuthManagerSpecialPage extends SpecialPage {
                                // passed to AuthManager. Normally we would display the form with an error message,
                                // but for the data we received via the redirect flow that would not be helpful at all.
                                // Let's just submit the data to AuthManager directly instead.
-                               LoggerFactory::getInstance( 'authmanager' )
+                               LoggerFactory::getInstance( 'authentication' )
                                        ->warning( 'Validation error on return', [ 'data' => $form->mFieldData,
                                                'status' => $status->getWikiText() ] );
                                $status = $this->handleFormSubmit( $form->mFieldData );
index 5dab221..8a2e0d6 100644 (file)
@@ -1342,196 +1342,12 @@ class FakeAuthTemplate extends BaseTemplate {
        }
 }
 
-/**
- * A horrible hack to handle AuthManager's feature flag. For other special pages this is done in
- * SpecialPageFactory, but LoginForm is used directly by some extensions. Will be killed as soon
- * as AuthManager is stable.
- */
-class LoginForm extends SpecialPage {
-       private $realLoginForm;
-
-       public function __construct( $request = null ) {
-               global $wgDisableAuthManager;
-               if ( $wgDisableAuthManager ) {
-                       $this->realLoginForm = new LoginFormPreAuthManager( $request );
-               } else {
-                       $this->realLoginForm = new LoginFormAuthManager( $request );
-               }
-       }
-
-       // proxy everything
-
-       public function __get( $name ) {
-               return $this->realLoginForm->$name;
-       }
-
-       public function __set( $name, $value ) {
-               $this->realLoginForm->$name = $value;
-       }
-
-       public function __call( $name, $args ) {
-               return call_user_func_array( [ $this->realLoginForm, $name ], $args );
-       }
-
-       public static function __callStatic( $name, $args ) {
-               global $wgDisableAuthManager;
-               return call_user_func_array( [ $wgDisableAuthManager ? LoginFormPreAuthManager::class
-                       : LoginFormAuthManager::class, $name ], $args );
-       }
-
-       // all public SpecialPage methods need to be proxied explicitly
-
-       public function getName() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getRestriction() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function isListed() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function setListed( $listed ) {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function listed( $x = null ) {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function isIncludable() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function including( $x = null ) {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getLocalName() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function isExpensive() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function isCached() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function isRestricted() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function userCanExecute( User $user ) {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function displayRestrictionError() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function checkPermissions() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function checkReadOnly() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function requireLogin(
-               $reasonMsg = 'exception-nologin-text', $titleMsg = 'exception-nologin'
-       ) {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function prefixSearchSubpages( $search, $limit, $offset ) {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function execute( $subPage ) {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getDescription() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       function getTitle( $subpage = false ) {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       function getPageTitle( $subpage = false ) {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function setContext( $context ) {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getContext() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getRequest() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getOutput() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getUser() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getSkin() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getLanguage() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getConfig() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getFullTitle() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function getFinalGroupName() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-       public function doesWrites() {
-               return call_user_func_array( [ $this->realLoginForm, __FUNCTION__ ], func_get_args() );
-       }
-
-       // no way to proxy constants and static properties
-
-       const SUCCESS = 0;
-       const NO_NAME = 1;
-       const ILLEGAL = 2;
-       const WRONG_PLUGIN_PASS = 3;
-       const NOT_EXISTS = 4;
-       const WRONG_PASS = 5;
-       const EMPTY_PASS = 6;
-       const RESET_PASS = 7;
-       const ABORTED = 8;
-       const CREATE_BLOCKED = 9;
-       const THROTTLED = 10;
-       const USER_BLOCKED = 11;
-       const NEED_TOKEN = 12;
-       const WRONG_TOKEN = 13;
-       const USER_MIGRATED = 14;
-
-       public static $statusCodes = [
-               self::SUCCESS => 'success',
-               self::NO_NAME => 'no_name',
-               self::ILLEGAL => 'illegal',
-               self::WRONG_PLUGIN_PASS => 'wrong_plugin_pass',
-               self::NOT_EXISTS => 'not_exists',
-               self::WRONG_PASS => 'wrong_pass',
-               self::EMPTY_PASS => 'empty_pass',
-               self::RESET_PASS => 'reset_pass',
-               self::ABORTED => 'aborted',
-               self::CREATE_BLOCKED => 'create_blocked',
-               self::THROTTLED => 'throttled',
-               self::USER_BLOCKED => 'user_blocked',
-               self::NEED_TOKEN => 'need_token',
-               self::WRONG_TOKEN => 'wrong_token',
-               self::USER_MIGRATED => 'user_migrated',
-       ];
-
-       public static $validErrorMessages = [
-               'exception-nologin-text',
-               'watchlistanontext',
-               'changeemail-no-info',
-               'resetpass-no-info',
-               'confirmemail_needlogin',
-               'prefsnologintext2',
-       ];
-}
-
 /**
  * LoginForm as a special page has been replaced by SpecialUserLogin and SpecialCreateAccount,
  * but some extensions called its public methods directly, so the class is retained as a
  * B/C wrapper. Anything that used it before should use AuthManager instead.
  */
-class LoginFormAuthManager extends SpecialPage {
+class LoginForm extends SpecialPage {
        const SUCCESS = 0;
        const NO_NAME = 1;
        const ILLEGAL = 2;
index 35ecc6e..00d8c4a 100644 (file)
@@ -61,12 +61,14 @@ class SpecialPage {
        protected $mContext;
 
        /**
-        * @var LinkRenderer|null
+        * @var \MediaWiki\Linker\LinkRenderer|null
         */
        private $linkRenderer;
 
        /**
         * Get a localised Title object for a specified special page name
+        * If you don't need a full Title object, consider using TitleValue through
+        * getTitleValueFor() below.
         *
         * @since 1.9
         * @since 1.21 $fragment parameter added
@@ -78,9 +80,24 @@ class SpecialPage {
         * @throws MWException
         */
        public static function getTitleFor( $name, $subpage = false, $fragment = '' ) {
+               return Title::newFromTitleValue(
+                       self::getTitleValueFor( $name, $subpage, $fragment )
+               );
+       }
+
+       /**
+        * Get a localised TitleValue object for a specified special page name
+        *
+        * @since 1.28
+        * @param string $name
+        * @param string|bool $subpage Subpage string, or false to not use a subpage
+        * @param string $fragment The link fragment (after the "#")
+        * @return TitleValue
+        */
+       public static function getTitleValueFor( $name, $subpage = false, $fragment = '' ) {
                $name = SpecialPageFactory::getLocalNameFor( $name, $subpage );
 
-               return Title::makeTitle( NS_SPECIAL, $name, $fragment );
+               return new TitleValue( NS_SPECIAL, $name, $fragment );
        }
 
        /**
@@ -834,7 +851,7 @@ class SpecialPage {
 
        /**
         * @since 1.28
-        * @return LinkRenderer
+        * @return \MediaWiki\Linker\LinkRenderer
         */
        protected function getLinkRenderer() {
                if ( $this->linkRenderer ) {
@@ -846,7 +863,7 @@ class SpecialPage {
 
        /**
         * @since 1.28
-        * @param LinkRenderer $linkRenderer
+        * @param \MediaWiki\Linker\LinkRenderer $linkRenderer
         */
        public function setLinkRenderer( LinkRenderer $linkRenderer ) {
                $this->linkRenderer = $linkRenderer;
index b69b28a..4356bc5 100644 (file)
@@ -84,8 +84,8 @@ class SpecialPageFactory {
 
                // Authentication
                'Userlogin' => 'SpecialUserLogin',
-               'Userlogout' => 'SpecialUserlogoutPreAuthManager',
-               'CreateAccount' => 'SpecialCreateAccountPreAuthManager',
+               'Userlogout' => 'SpecialUserLogout',
+               'CreateAccount' => 'SpecialCreateAccount',
                'LinkAccounts' => 'SpecialLinkAccounts',
                'UnlinkAccounts' => 'SpecialUnlinkAccounts',
                'ChangeCredentials' => 'SpecialChangeCredentials',
@@ -96,9 +96,9 @@ class SpecialPageFactory {
                'Block' => 'SpecialBlock',
                'Unblock' => 'SpecialUnblock',
                'BlockList' => 'SpecialBlockList',
-               'ChangePassword' => 'SpecialChangePasswordPreAuthManager',
+               'ChangePassword' => 'SpecialChangePassword',
                'BotPasswords' => 'SpecialBotPasswords',
-               'PasswordReset' => 'SpecialPasswordResetPreAuthManager',
+               'PasswordReset' => 'SpecialPasswordReset',
                'DeletedContributions' => 'DeletedContributionsPage',
                'Preferences' => 'SpecialPreferences',
                'ResetTokens' => 'SpecialResetTokens',
@@ -231,7 +231,6 @@ class SpecialPageFactory {
                global $wgDisableInternalSearch, $wgEmailAuthentication;
                global $wgEnableEmail, $wgEnableJavaScriptTest;
                global $wgPageLanguageUseDB, $wgContentHandlerUseDB;
-               global $wgDisableAuthManager;
 
                if ( !is_array( self::$list ) ) {
 
@@ -247,7 +246,7 @@ class SpecialPageFactory {
                        }
 
                        if ( $wgEnableEmail ) {
-                               self::$list['ChangeEmail'] = 'SpecialChangeEmailPreAuthManager';
+                               self::$list['ChangeEmail'] = 'SpecialChangeEmail';
                        }
 
                        if ( $wgEnableJavaScriptTest ) {
@@ -261,20 +260,6 @@ class SpecialPageFactory {
                                self::$list['ChangeContentModel'] = 'SpecialChangeContentModel';
                        }
 
-                       // horrible hack to allow selection between old and new classes via a feature flag - T110756
-                       // will be removed once AuthManager is stable
-                       if ( !$wgDisableAuthManager ) {
-                               self::$list = array_map( function ( $class ) {
-                                       return preg_replace( '/PreAuthManager$/', '', $class );
-                               }, self::$list );
-                               self::$list['Userlogout'] = 'SpecialUserLogout'; // case matters
-                       } else {
-                               self::$list['Userlogin'] = 'LoginForm';
-                               self::$list = array_diff_key( self::$list, array_fill_keys( [
-                                       'LinkAccounts', 'UnlinkAccounts', 'ChangeCredentials', 'RemoveCredentials',
-                               ], true ) );
-                       }
-
                        // Add extension special pages
                        self::$list = array_merge( self::$list, $wgSpecialPages );
 
@@ -714,6 +699,8 @@ class SpecialPageFactory {
                }
 
                if ( $subpage !== false && !is_null( $subpage ) ) {
+                       // Make sure it's in dbkey form
+                       $subpage = str_replace( ' ', '_', $subpage );
                        $name = "$name/$subpage";
                }
 
index 4da8049..d98504d 100644 (file)
@@ -184,6 +184,7 @@ class SpecialChangeCredentials extends AuthManagerSpecialPage {
                        $groupedRequests[(string)$info['provider']][] = $req;
                }
 
+               $linkRenderer = $this->getLinkRenderer();
                $out->addHTML( Html::openElement( 'dl' ) );
                foreach ( $groupedRequests as $group => $members ) {
                        $out->addHTML( Html::element( 'dt', [], $group ) );
@@ -191,8 +192,10 @@ class SpecialChangeCredentials extends AuthManagerSpecialPage {
                                /** @var AuthenticationRequest $req */
                                $info = $req->describeCredentials();
                                $out->addHTML( Html::rawElement( 'dd', [],
-                                       Linker::link( $this->getPageTitle( $req->getUniqueId() ),
-                                               htmlspecialchars( $info['account'], ENT_QUOTES ) )
+                                       $linkRenderer->makeLink(
+                                               $this->getPageTitle( $req->getUniqueId() ),
+                                               $info['account']
+                                       )
                                ) );
                        }
                }
index 0a98721..6aeb2c3 100644 (file)
@@ -363,7 +363,7 @@ class SpecialContributions extends IncludableSpecialPage {
                        if ( $sp->getUser()->isAllowed( 'suppressionlog' ) ) {
                                $tools['log-suppression'] = $linkRenderer->makeKnownLink(
                                        SpecialPage::getTitleFor( 'Log', 'suppress' ),
-                                       $sp->msg( 'sp-contributions-suppresslog' )->text(),
+                                       $sp->msg( 'sp-contributions-suppresslog', $username )->text(),
                                        [],
                                        [ 'offender' => $username ]
                                );
@@ -385,7 +385,7 @@ class SpecialContributions extends IncludableSpecialPage {
                if ( $sp->getUser()->isAllowed( 'deletedhistory' ) ) {
                        $tools['deletedcontribs'] = $linkRenderer->makeKnownLink(
                                SpecialPage::getTitleFor( 'DeletedContributions', $username ),
-                               $sp->msg( 'sp-contributions-deleted' )->text()
+                               $sp->msg( 'sp-contributions-deleted', $username )->text()
                        );
                }
 
index f06a192..2b43a49 100644 (file)
@@ -159,7 +159,7 @@ class SpecialCreateAccount extends LoginSignupSpecialPage {
        }
 
        protected function logAuthResult( $success, $status = null ) {
-               LoggerFactory::getInstance( 'authmanager' )->info( 'Account creation attempt', [
+               LoggerFactory::getInstance( 'authevents' )->info( 'Account creation attempt', [
                        'event' => 'accountcreation',
                        'successful' => $success,
                        'status' => $status,
index 627dd2c..a5a45d5 100644 (file)
@@ -2,7 +2,6 @@
 /**
  * @defgroup Watchlist Users watchlist handling
  */
-use MediaWiki\Linker\LinkTarget;
 
 /**
  * Implements Special:EditWatchlist
@@ -27,6 +26,8 @@ use MediaWiki\Linker\LinkTarget;
  * @ingroup Watchlist
  */
 
+use MediaWiki\Linker\LinkRenderer;
+use MediaWiki\Linker\LinkTarget;
 use MediaWiki\MediaWikiServices;
 
 /**
@@ -138,7 +139,13 @@ class SpecialEditWatchlist extends UnlistedSpecialPage {
        protected function outputSubtitle() {
                $out = $this->getOutput();
                $out->addSubtitle( $this->msg( 'watchlistfor2', $this->getUser()->getName() )
-                       ->rawParams( SpecialEditWatchlist::buildTools( null ) ) );
+                       ->rawParams(
+                               self::buildTools(
+                                       $this->getLanguage(),
+                                       $this->getLinkRenderer()
+                               )
+                       )
+               );
        }
 
        /**
@@ -277,7 +284,7 @@ class SpecialEditWatchlist extends UnlistedSpecialPage {
         * @param string $output
         */
        private function showTitles( $titles, &$output ) {
-               $talk = $this->msg( 'talkpagelinktext' )->escaped();
+               $talk = $this->msg( 'talkpagelinktext' )->text();
                // Do a batch existence check
                $batch = new LinkBatch();
                if ( count( $titles ) >= 100 ) {
@@ -300,6 +307,7 @@ class SpecialEditWatchlist extends UnlistedSpecialPage {
                // Print out the list
                $output .= "<ul>\n";
 
+               $linkRenderer = $this->getLinkRenderer();
                foreach ( $titles as $title ) {
                        if ( !$title instanceof Title ) {
                                $title = Title::newFromText( $title );
@@ -307,9 +315,9 @@ class SpecialEditWatchlist extends UnlistedSpecialPage {
 
                        if ( $title instanceof Title ) {
                                $output .= '<li>' .
-                                       Linker::link( $title ) . ' ' .
+                                       $linkRenderer->makeLink( $title ) . ' ' .
                                        $this->msg( 'parentheses' )->rawParams(
-                                               Linker::link( $title->getTalkPage(), $talk )
+                                               $linkRenderer->makeLink( $title->getTalkPage(), $talk )
                                        )->escaped() .
                                        "</li>\n";
                        }
@@ -610,26 +618,27 @@ class SpecialEditWatchlist extends UnlistedSpecialPage {
         * @return string
         */
        private function buildRemoveLine( $title ) {
-               $link = Linker::link( $title );
+               $linkRenderer = $this->getLinkRenderer();
+               $link = $linkRenderer->makeLink( $title );
 
-               $tools['talk'] = Linker::link(
+               $tools['talk'] = $linkRenderer->makeLink(
                        $title->getTalkPage(),
-                       $this->msg( 'talkpagelinktext' )->escaped()
+                       $this->msg( 'talkpagelinktext' )->text()
                );
 
                if ( $title->exists() ) {
-                       $tools['history'] = Linker::linkKnown(
+                       $tools['history'] = $linkRenderer->makeKnownLink(
                                $title,
-                               $this->msg( 'history_short' )->escaped(),
+                               $this->msg( 'history_short' )->text(),
                                [],
                                [ 'action' => 'history' ]
                        );
                }
 
                if ( $title->getNamespace() == NS_USER && !$title->isSubpage() ) {
-                       $tools['contributions'] = Linker::linkKnown(
+                       $tools['contributions'] = $linkRenderer->makeKnownLink(
                                SpecialPage::getTitleFor( 'Contributions', $title->getText() ),
-                               $this->msg( 'contributions' )->escaped()
+                               $this->msg( 'contributions' )->text()
                        );
                }
 
@@ -724,11 +733,19 @@ class SpecialEditWatchlist extends UnlistedSpecialPage {
         * Build a set of links for convenient navigation
         * between watchlist viewing and editing modes
         *
-        * @param null $unused
+        * @param Language $lang
+        * @param LinkRenderer|null $linkRenderer
         * @return string
         */
-       public static function buildTools( $unused ) {
-               global $wgLang;
+       public static function buildTools( $lang, LinkRenderer $linkRenderer = null ) {
+               if ( !$lang instanceof Language ) {
+                       // back-compat where the first parameter was $unused
+                       global $wgLang;
+                       $lang = $wgLang;
+               }
+               if ( !$linkRenderer ) {
+                       $linkRenderer = MediaWikiServices::getInstance()->getLinkRenderer();
+               }
 
                $tools = [];
                $modes = [
@@ -740,16 +757,16 @@ class SpecialEditWatchlist extends UnlistedSpecialPage {
 
                foreach ( $modes as $mode => $arr ) {
                        // can use messages 'watchlisttools-view', 'watchlisttools-edit', 'watchlisttools-raw'
-                       $tools[] = Linker::linkKnown(
+                       $tools[] = $linkRenderer->makeKnownLink(
                                SpecialPage::getTitleFor( $arr[0], $arr[1] ),
-                               wfMessage( "watchlisttools-{$mode}" )->escaped()
+                               wfMessage( "watchlisttools-{$mode}" )->text()
                        );
                }
 
                return Html::rawElement(
                        'span',
                        [ 'class' => 'mw-watchlist-toollinks' ],
-                       wfMessage( 'parentheses' )->rawParams( $wgLang->pipeList( $tools ) )->escaped()
+                       wfMessage( 'parentheses' )->rawParams( $lang->pipeList( $tools ) )->escaped()
                );
        }
 }
index 5d36a3c..0e2e7db 100644 (file)
@@ -118,7 +118,7 @@ class SpecialJavaScriptTest extends SpecialPage {
                        . 'window.__karma__.loaded = function () {};'
                        . '}';
 
-               // The below is essentially a pure-javascript version of OutputPage::getHeadScripts.
+               // The below is essentially a pure-javascript version of OutputPage::headElement().
                $startup = $rl->makeModuleResponse( $startupContext, [
                        'startup' => $rl->getModule( 'startup' ),
                ] );
@@ -166,7 +166,7 @@ class SpecialJavaScriptTest extends SpecialPage {
                        [ 'raw' => true, 'sync' => true ]
                );
 
-               $head = implode( "\n", array_merge( $styles['html'], $scripts['html'] ) );
+               $head = implode( "\n", [ $styles, $scripts ] );
                $summary = $this->getSummaryHtml();
                $html = <<<HTML
 <!DOCTYPE html>
index b8316f3..3ead08a 100644 (file)
@@ -94,7 +94,7 @@ class MostlinkedCategoriesPage extends QueryPage {
                }
 
                $text = $wgContLang->convert( $nt->getText() );
-               $plink = Linker::link( $nt, htmlspecialchars( $text ) );
+               $plink = $this->getLinkRenderer()->makeLink( $nt, $text );
                $nlinks = $this->msg( 'nmembers' )->numParams( $result->value )->escaped();
 
                return $this->getLanguage()->specialList( $plink, $nlinks );
index d2513ed..718a6dc 100644 (file)
@@ -349,7 +349,6 @@ class SpecialNewpages extends IncludableSpecialPage {
 
                if ( $this->patrollable( $result ) ) {
                        $classes[] = 'not-patrolled';
-                       $this->getOutput()->addModuleStyles( 'mediawiki.page.patrol' );
                }
 
                # Add a class for zero byte pages
index 20f2fc8..a76b511 100644 (file)
@@ -104,19 +104,20 @@ class ShortPagesPage extends QueryPage {
                                Linker::getInvalidTitleDescription( $this->getContext(), $result->namespace, $result->title ) );
                }
 
-               $hlink = Linker::linkKnown(
+               $linkRenderer = $this->getLinkRenderer();
+               $hlink = $linkRenderer->makeKnownLink(
                        $title,
-                       $this->msg( 'hist' )->escaped(),
+                       $this->msg( 'hist' )->text(),
                        [],
                        [ 'action' => 'history' ]
                );
                $hlinkInParentheses = $this->msg( 'parentheses' )->rawParams( $hlink )->escaped();
 
                if ( $this->isCached() ) {
-                       $plink = Linker::link( $title );
+                       $plink = $linkRenderer->makeLink( $title );
                        $exists = $title->exists();
                } else {
-                       $plink = Linker::linkKnown( $title );
+                       $plink = $linkRenderer->makeKnownLink( $title );
                        $exists = true;
                }
 
index 3ebf5d0..e957b3c 100644 (file)
@@ -175,12 +175,13 @@ class SpecialTags extends SpecialPage {
                $newRow = '';
                $newRow .= Xml::tags( 'td', null, Xml::element( 'code', null, $tag ) );
 
+               $linkRenderer = $this->getLinkRenderer();
                $disp = ChangeTags::tagDescription( $tag );
                if ( $showEditLinks ) {
                        $disp .= ' ';
-                       $editLink = Linker::link(
+                       $editLink = $linkRenderer->makeLink(
                                $this->msg( "tag-$tag" )->inContentLanguage()->getTitle(),
-                               $this->msg( 'tags-edit' )->escaped()
+                               $this->msg( 'tags-edit' )->text()
                        );
                        $disp .= $this->msg( 'parentheses' )->rawParams( $editLink )->escaped();
                }
@@ -190,9 +191,9 @@ class SpecialTags extends SpecialPage {
                $desc = !$msg->exists() ? '' : $msg->parse();
                if ( $showEditLinks ) {
                        $desc .= ' ';
-                       $editDescLink = Linker::link(
+                       $editDescLink = $linkRenderer->makeLink(
                                $this->msg( "tag-$tag-description" )->inContentLanguage()->getTitle(),
-                               $this->msg( 'tags-edit' )->escaped()
+                               $this->msg( 'tags-edit' )->text()
                        );
                        $desc .= $this->msg( 'parentheses' )->rawParams( $editDescLink )->escaped();
                }
@@ -216,14 +217,16 @@ class SpecialTags extends SpecialPage {
                $activeMsg = ( $isActive ? 'tags-active-yes' : 'tags-active-no' );
                $newRow .= Xml::tags( 'td', null, $this->msg( $activeMsg )->escaped() );
 
-               $hitcountLabel = $this->msg( 'tags-hitcount' )->numParams( $hitcount )->escaped();
+               $hitcountLabelMsg = $this->msg( 'tags-hitcount' )->numParams( $hitcount );
                if ( $this->getConfig()->get( 'UseTagFilter' ) ) {
-                       $hitcountLabel = Linker::link(
+                       $hitcountLabel = $linkRenderer->makeLink(
                                SpecialPage::getTitleFor( 'Recentchanges' ),
-                               $hitcountLabel,
+                               $hitcountLabelMsg->text(),
                                [],
                                [ 'tagfilter' => $tag ]
                        );
+               } else {
+                       $hitcountLabel = $hitcountLabelMsg->escaped();
                }
 
                // add raw $hitcount for sorting, because tags-hitcount contains numbers and letters
@@ -234,8 +237,9 @@ class SpecialTags extends SpecialPage {
 
                // delete
                if ( $showDeleteActions && ChangeTags::canDeleteTag( $tag )->isOK() ) {
-                       $actionLinks[] = Linker::linkKnown( $this->getPageTitle( 'delete' ),
-                               $this->msg( 'tags-delete' )->escaped(),
+                       $actionLinks[] = $linkRenderer->makeKnownLink(
+                               $this->getPageTitle( 'delete' ),
+                               $this->msg( 'tags-delete' )->text(),
                                [],
                                [ 'tag' => $tag ] );
                }
@@ -244,16 +248,18 @@ class SpecialTags extends SpecialPage {
 
                        // activate
                        if ( ChangeTags::canActivateTag( $tag )->isOK() ) {
-                               $actionLinks[] = Linker::linkKnown( $this->getPageTitle( 'activate' ),
-                                       $this->msg( 'tags-activate' )->escaped(),
+                               $actionLinks[] = $linkRenderer->makeKnownLink(
+                                       $this->getPageTitle( 'activate' ),
+                                       $this->msg( 'tags-activate' )->text(),
                                        [],
                                        [ 'tag' => $tag ] );
                        }
 
                        // deactivate
                        if ( ChangeTags::canDeactivateTag( $tag )->isOK() ) {
-                               $actionLinks[] = Linker::linkKnown( $this->getPageTitle( 'deactivate' ),
-                                       $this->msg( 'tags-deactivate' )->escaped(),
+                               $actionLinks[] = $linkRenderer->makeKnownLink(
+                                       $this->getPageTitle( 'deactivate' ),
+                                       $this->msg( 'tags-deactivate' )->text(),
                                        [],
                                        [ 'tag' => $tag ] );
                        }
index 5d230c0..65f0680 100644 (file)
@@ -354,6 +354,9 @@ class PageArchive {
         * Once restored, the items will be removed from the archive tables.
         * The deletion log will be updated with an undeletion notice.
         *
+        * This also sets Status objects, $this->fileStatus and $this->revisionStatus
+        * (depending what operations are attempted).
+        *
         * @param array $timestamps Pass an empty array to restore all revisions,
         *   otherwise list the ones to undelete.
         * @param string $comment
@@ -439,9 +442,8 @@ class PageArchive {
        }
 
        /**
-        * This is the meaty bit -- restores archived revisions of the given page
-        * to the cur/old tables. If the page currently exists, all revisions will
-        * be stuffed into old, otherwise the most recent will go into cur.
+        * This is the meaty bit -- It restores archived revisions of the given page
+        * to the revision table.
         *
         * @param array $timestamps Pass an empty array to restore all revisions,
         *   otherwise list the ones to undelete.
@@ -455,8 +457,10 @@ class PageArchive {
                        throw new ReadOnlyError();
                }
 
-               $restoreAll = empty( $timestamps );
                $dbw = wfGetDB( DB_MASTER );
+               $dbw->startAtomic( __METHOD__ );
+
+               $restoreAll = empty( $timestamps );
 
                # Does this page already exist? We'll have to update it...
                $article = WikiPage::factory( $this->title );
@@ -477,11 +481,9 @@ class PageArchive {
                        # Page already exists. Import the history, and if necessary
                        # we'll update the latest revision field in the record.
 
-                       $previousRevId = $page->page_latest;
-
                        # Get the time span of this page
                        $previousTimestamp = $dbw->selectField( 'revision', 'rev_timestamp',
-                               [ 'rev_id' => $previousRevId ],
+                               [ 'rev_id' => $page->page_latest ],
                                __METHOD__ );
 
                        if ( $previousTimestamp === false ) {
@@ -489,13 +491,13 @@ class PageArchive {
 
                                $status = Status::newGood( 0 );
                                $status->warning( 'undeleterevision-missing' );
+                               $dbw->endAtomic( __METHOD__ );
 
                                return $status;
                        }
                } else {
                        # Have to create a new article...
                        $makepage = true;
-                       $previousRevId = 0;
                        $previousTimestamp = 0;
                }
 
@@ -508,7 +510,9 @@ class PageArchive {
                }
 
                $fields = [
+                       'ar_id',
                        'ar_rev_id',
+                       'rev_id',
                        'ar_text',
                        'ar_comment',
                        'ar_user',
@@ -531,11 +535,14 @@ class PageArchive {
                /**
                 * Select each archived revision...
                 */
-               $result = $dbw->select( 'archive',
+               $result = $dbw->select(
+                       [ 'archive', 'revision' ],
                        $fields,
                        $oldWhere,
                        __METHOD__,
-                       /* options */ [ 'ORDER BY' => 'ar_timestamp' ]
+                       /* options */
+                       [ 'ORDER BY' => 'ar_timestamp' ],
+                       [ 'revision' => [ 'LEFT JOIN', 'ar_rev_id=rev_id' ] ]
                );
 
                $rev_count = $result->numRows();
@@ -544,116 +551,182 @@ class PageArchive {
 
                        $status = Status::newGood( 0 );
                        $status->warning( "undelete-no-results" );
+                       $dbw->endAtomic( __METHOD__ );
 
                        return $status;
                }
 
-               $result->seek( $rev_count - 1 ); // move to last
-               $row = $result->fetchObject(); // get newest archived rev
-               $oldPageId = (int)$row->ar_page_id; // pass this to ArticleUndelete hook
-               $result->seek( 0 ); // move back
+               // We use ar_id because there can be duplicate ar_rev_id even for the same
+               // page.  In this case, we may be able to restore the first one.
+               $restoreFailedArIds = [];
 
-               // grab the content to check consistency with global state before restoring the page.
-               $revision = Revision::newFromArchiveRow( $row,
-                       [
-                               'title' => $article->getTitle(), // used to derive default content model
-                       ]
-               );
-               $user = User::newFromName( $revision->getUserText( Revision::RAW ), false );
-               $content = $revision->getContent( Revision::RAW );
+               // Map rev_id to the ar_id that is allowed to use it.  When checking later,
+               // if it doesn't match, the current ar_id can not be restored.
 
-               // NOTE: article ID may not be known yet. prepareSave() should not modify the database.
-               $status = $content->prepareSave( $article, 0, -1, $user );
+               // Value can be an ar_id or -1 (-1 means no ar_id can use it, since the
+               // rev_id is taken before we even start the restore).
+               $allowedRevIdToArIdMap = [];
 
-               if ( !$status->isOK() ) {
-                       return $status;
-               }
+               $latestRestorableRow = null;
 
-               if ( $makepage ) {
-                       // Check the state of the newest to-be version...
-                       if ( !$unsuppress && ( $row->ar_deleted & Revision::DELETED_TEXT ) ) {
-                               return Status::newFatal( "undeleterevdel" );
+               foreach ( $result as $row ) {
+                       if ( $row->ar_rev_id ) {
+                               // rev_id is taken even before we start restoring.
+                               if ( $row->ar_rev_id === $row->rev_id ) {
+                                       $restoreFailedArIds[] = $row->ar_id;
+                                       $allowedRevIdToArIdMap[$row->ar_rev_id] = -1;
+                               } else {
+                                       // rev_id is not taken yet in the DB, but it might be taken
+                                       // by a prior revision in the same restore operation. If
+                                       // not, we need to reserve it.
+                                       if ( isset( $allowedRevIdToArIdMap[$row->ar_rev_id] ) ) {
+                                               $restoreFailedArIds[] = $row->ar_id;
+                                       } else {
+                                               $allowedRevIdToArIdMap[$row->ar_rev_id] = $row->ar_id;
+                                               $latestRestorableRow = $row;
+                                       }
+                               }
+                       } else {
+                               // If ar_rev_id is null, there can't be a collision, and a
+                               // rev_id will be chosen automatically.
+                               $latestRestorableRow = $row;
                        }
-                       // Safe to insert now...
-                       $newid = $article->insertOn( $dbw, $row->ar_page_id );
-                       if ( $newid === false ) {
-                               // The old ID is reserved; let's pick another
-                               $newid = $article->insertOn( $dbw );
+               }
+
+               $result->seek( 0 ); // move back
+
+               $oldPageId = 0;
+               if ( $latestRestorableRow !== null ) {
+                       $oldPageId = (int)$latestRestorableRow->ar_page_id; // pass this to ArticleUndelete hook
+
+                       // grab the content to check consistency with global state before restoring the page.
+                       $revision = Revision::newFromArchiveRow( $latestRestorableRow,
+                               [
+                                       'title' => $article->getTitle(), // used to derive default content model
+                               ]
+                       );
+                       $user = User::newFromName( $revision->getUserText( Revision::RAW ), false );
+                       $content = $revision->getContent( Revision::RAW );
+
+                       // NOTE: article ID may not be known yet. prepareSave() should not modify the database.
+                       $status = $content->prepareSave( $article, 0, -1, $user );
+                       if ( !$status->isOK() ) {
+                               $dbw->endAtomic( __METHOD__ );
+
+                               return $status;
                        }
-                       $pageId = $newid;
+               }
+
+               $newid = false; // newly created page ID
+               $restored = 0; // number of revisions restored
+               /** @var Revision $revision */
+               $revision = null;
+
+               // If there are no restorable revisions, we can skip most of the steps.
+               if ( $latestRestorableRow === null ) {
+                       $failedRevisionCount = $rev_count;
                } else {
-                       // Check if a deleted revision will become the current revision...
-                       if ( $row->ar_timestamp > $previousTimestamp ) {
+                       if ( $makepage ) {
                                // Check the state of the newest to-be version...
-                               if ( !$unsuppress && ( $row->ar_deleted & Revision::DELETED_TEXT ) ) {
+                               if ( !$unsuppress
+                                       && ( $latestRestorableRow->ar_deleted & Revision::DELETED_TEXT )
+                               ) {
+                                       $dbw->endAtomic( __METHOD__ );
+
                                        return Status::newFatal( "undeleterevdel" );
                                }
+                               // Safe to insert now...
+                               $newid = $article->insertOn( $dbw, $latestRestorableRow->ar_page_id );
+                               if ( $newid === false ) {
+                                       // The old ID is reserved; let's pick another
+                                       $newid = $article->insertOn( $dbw );
+                               }
+                               $pageId = $newid;
+                       } else {
+                               // Check if a deleted revision will become the current revision...
+                               if ( $latestRestorableRow->ar_timestamp > $previousTimestamp ) {
+                                       // Check the state of the newest to-be version...
+                                       if ( !$unsuppress
+                                               && ( $latestRestorableRow->ar_deleted & Revision::DELETED_TEXT )
+                                       ) {
+                                               $dbw->endAtomic( __METHOD__ );
+
+                                               return Status::newFatal( "undeleterevdel" );
+                                       }
+                               }
+
+                               $newid = false;
+                               $pageId = $article->getId();
                        }
 
-                       $newid = false;
-                       $pageId = $article->getId();
-               }
+                       foreach ( $result as $row ) {
+                               // Check for key dupes due to needed archive integrity.
+                               if ( $row->ar_rev_id && $allowedRevIdToArIdMap[$row->ar_rev_id] !== $row->ar_id ) {
+                                       continue;
+                               }
+                               // Insert one revision at a time...maintaining deletion status
+                               // unless we are specifically removing all restrictions...
+                               $revision = Revision::newFromArchiveRow( $row,
+                                       [
+                                               'page' => $pageId,
+                                               'title' => $this->title,
+                                               'deleted' => $unsuppress ? 0 : $row->ar_deleted
+                                       ] );
 
-               $revision = null;
-               $restored = 0;
+                               $revision->insertOn( $dbw );
+                               $restored++;
 
-               foreach ( $result as $row ) {
-                       // Check for key dupes due to needed archive integrity.
-                       if ( $row->ar_rev_id ) {
-                               $exists = $dbw->selectField( 'revision', '1',
-                                       [ 'rev_id' => $row->ar_rev_id ], __METHOD__ );
-                               if ( $exists ) {
-                                       continue; // don't throw DB errors
-                               }
+                               Hooks::run( 'ArticleRevisionUndeleted',
+                                       [ &$this->title, $revision, $row->ar_page_id ] );
                        }
-                       // Insert one revision at a time...maintaining deletion status
-                       // unless we are specifically removing all restrictions...
-                       $revision = Revision::newFromArchiveRow( $row,
-                               [
-                                       'page' => $pageId,
-                                       'title' => $this->title,
-                                       'deleted' => $unsuppress ? 0 : $row->ar_deleted
-                               ] );
-
-                       $revision->insertOn( $dbw );
-                       $restored++;
 
-                       Hooks::run( 'ArticleRevisionUndeleted', [ &$this->title, $revision, $row->ar_page_id ] );
-               }
-               # Now that it's safely stored, take it out of the archive
-               $dbw->delete( 'archive',
-                       $oldWhere,
-                       __METHOD__ );
+                       // Now that it's safely stored, take it out of the archive
+                       // Don't delete rows that we failed to restore
+                       $toDeleteConds = $oldWhere;
+                       $failedRevisionCount = count( $restoreFailedArIds );
+                       if ( $failedRevisionCount > 0 ) {
+                               $toDeleteConds[] = 'ar_id NOT IN ( ' . $dbw->makeList( $restoreFailedArIds ) . ' )';
+                       }
 
-               // Was anything restored at all?
-               if ( $restored == 0 ) {
-                       return Status::newGood( 0 );
+                       $dbw->delete( 'archive',
+                               $toDeleteConds,
+                               __METHOD__ );
                }
 
-               $created = (bool)$newid;
+               $status = Status::newGood( $restored );
 
-               // Attach the latest revision to the page...
-               $wasnew = $article->updateIfNewerOn( $dbw, $revision, $previousRevId );
-               if ( $created || $wasnew ) {
-                       // Update site stats, link tables, etc
-                       $article->doEditUpdates(
-                               $revision,
-                               User::newFromName( $revision->getUserText( Revision::RAW ), false ),
-                               [
-                                       'created' => $created,
-                                       'oldcountable' => $oldcountable,
-                                       'restored' => true
-                               ]
-                       );
+               if ( $failedRevisionCount > 0 ) {
+                       $status->warning(
+                               wfMessage( 'undeleterevision-duplicate-revid', $failedRevisionCount ) );
                }
 
-               Hooks::run( 'ArticleUndelete', [ &$this->title, $created, $comment, $oldPageId ] );
+               // Was anything restored at all?
+               if ( $restored ) {
+                       $created = (bool)$newid;
+                       // Attach the latest revision to the page...
+                       $wasnew = $article->updateIfNewerOn( $dbw, $revision );
+                       if ( $created || $wasnew ) {
+                               // Update site stats, link tables, etc
+                               $article->doEditUpdates(
+                                       $revision,
+                                       User::newFromName( $revision->getUserText( Revision::RAW ), false ),
+                                       [
+                                               'created' => $created,
+                                               'oldcountable' => $oldcountable,
+                                               'restored' => true
+                                       ]
+                               );
+                       }
 
-               if ( $this->title->getNamespace() == NS_FILE ) {
-                       DeferredUpdates::addUpdate( new HTMLCacheUpdate( $this->title, 'imagelinks' ) );
+                       Hooks::run( 'ArticleUndelete', [ &$this->title, $created, $comment, $oldPageId ] );
+                       if ( $this->title->getNamespace() == NS_FILE ) {
+                               DeferredUpdates::addUpdate( new HTMLCacheUpdate( $this->title, 'imagelinks' ) );
+                       }
                }
 
-               return Status::newGood( $restored );
+               $dbw->endAtomic( __METHOD__ );
+
+               return $status;
        }
 
        /**
index bfb52e8..6ca1100 100644 (file)
@@ -339,7 +339,13 @@ class SpecialUpload extends SpecialPage {
         * @param string $message HTML message to be passed to mainUploadForm
         */
        protected function showRecoverableUploadError( $message ) {
-               $sessionKey = $this->mUpload->stashFile()->getFileKey();
+               $stashStatus = $this->mUpload->tryStashFile( $this->getUser() );
+               if ( $stashStatus->isGood() ) {
+                       $sessionKey = $stashStatus->getValue()->getFileKey();
+               } else {
+                       $sessionKey = null;
+                       // TODO Add a warning message about the failure to stash here?
+               }
                $message = '<h2>' . $this->msg( 'uploaderror' )->escaped() . "</h2>\n" .
                        '<div class="error">' . $message . "</div>\n";
 
@@ -368,7 +374,13 @@ class SpecialUpload extends SpecialPage {
                        return false;
                }
 
-               $sessionKey = $this->mUpload->stashFile()->getFileKey();
+               $stashStatus = $this->mUpload->tryStashFile( $this->getUser() );
+               if ( $stashStatus->isGood() ) {
+                       $sessionKey = $stashStatus->getValue()->getFileKey();
+               } else {
+                       $sessionKey = null;
+                       // TODO Add a warning message about the failure to stash here?
+               }
 
                // Add styles for the warning, reused from the live preview
                $this->getOutput()->addModuleStyles( 'mediawiki.special.upload.styles' );
index 555fe5c..1412324 100644 (file)
@@ -391,17 +391,21 @@ class SpecialUploadStash extends UnlistedSpecialPage {
                if ( $files && count( $files ) ) {
                        sort( $files );
                        $fileListItemsHtml = '';
+                       $linkRenderer = $this->getLinkRenderer();
                        foreach ( $files as $file ) {
-                               $itemHtml = Linker::linkKnown( $this->getPageTitle( "file/$file" ), htmlspecialchars( $file ) );
+                               $itemHtml = $linkRenderer->makeKnownLink(
+                                       $this->getPageTitle( "file/$file" ),
+                                       $file
+                               );
                                try {
                                        $fileObj = $this->stash->getFile( $file );
                                        $thumb = $fileObj->generateThumbName( $file, [ 'width' => 220 ] );
                                        $itemHtml .=
                                                $this->msg( 'word-separator' )->escaped() .
                                                $this->msg( 'parentheses' )->rawParams(
-                                                       Linker::linkKnown(
+                                                       $linkRenderer->makeKnownLink(
                                                                $this->getPageTitle( "thumb/$file/$thumb" ),
-                                                               $this->msg( 'uploadstash-thumbnail' )->escaped()
+                                                               $this->msg( 'uploadstash-thumbnail' )->text()
                                                        )
                                                )->escaped();
                                } catch ( Exception $e ) {
index 21f5659..253cd50 100644 (file)
@@ -153,7 +153,7 @@ class SpecialUserLogin extends LoginSignupSpecialPage {
        }
 
        protected function logAuthResult( $success, $status = null ) {
-               LoggerFactory::getInstance( 'authmanager' )->info( 'Login attempt', [
+               LoggerFactory::getInstance( 'authevents' )->info( 'Login attempt', [
                        'event' => 'login',
                        'successful' => $success,
                        'status' => $status,
index 58cde7e..17d77ba 100644 (file)
@@ -429,7 +429,10 @@ class SpecialWatchlist extends ChangesListSpecialPage {
 
                $out->addSubtitle(
                        $this->msg( 'watchlistfor2', $user->getName() )
-                               ->rawParams( SpecialEditWatchlist::buildTools( null ) )
+                               ->rawParams( SpecialEditWatchlist::buildTools(
+                                       $this->getLanguage(),
+                                       $this->getLinkRenderer()
+                               ) )
                );
 
                $this->setTopText( $opts );
diff --git a/includes/specials/pre-authmanager/README b/includes/specials/pre-authmanager/README
deleted file mode 100644 (file)
index 1cfdd5f..0000000
+++ /dev/null
@@ -1,10 +0,0 @@
-This directory temporarily hosts pre-AuthManager code as a way of feature-flagging.
-Class names are postfixed with 'PreAuthManager' and SpecialPageFactory adds/removes
-that postfix based on the feature flag.
-
-This is a horrible hack that will only be in place for a few weeks, to allow instant
-rollback while AuthManager is tested in WMF production and major problems are ironed
-out. In the past such issues have been handled via deployment branches, but that
-meant blocking the work of all WMF developers from being deployed. This is hoped
-to be a less disruptive method.
-
diff --git a/includes/specials/pre-authmanager/SpecialChangeEmail.php b/includes/specials/pre-authmanager/SpecialChangeEmail.php
deleted file mode 100644 (file)
index 7861562..0000000
+++ /dev/null
@@ -1,216 +0,0 @@
-<?php
-/**
- * Implements Special:ChangeEmail
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- * @ingroup SpecialPage
- */
-
-/**
- * Let users change their email address.
- *
- * @ingroup SpecialPage
- */
-class SpecialChangeEmailPreAuthManager extends FormSpecialPage {
-       /**
-        * @var Status
-        */
-       private $status;
-
-       public function __construct() {
-               parent::__construct( 'ChangeEmail', 'editmyprivateinfo' );
-       }
-
-       public function doesWrites() {
-               return true;
-       }
-
-       /**
-        * @return bool
-        */
-       public function isListed() {
-               global $wgAuth;
-
-               return $wgAuth->allowPropChange( 'emailaddress' );
-       }
-
-       /**
-        * Main execution point
-        * @param string $par
-        */
-       function execute( $par ) {
-               $out = $this->getOutput();
-               $out->disallowUserJs();
-
-               parent::execute( $par );
-       }
-
-       protected function checkExecutePermissions( User $user ) {
-               global $wgAuth;
-
-               if ( !$wgAuth->allowPropChange( 'emailaddress' ) ) {
-                       throw new ErrorPageError( 'changeemail', 'cannotchangeemail' );
-               }
-
-               $this->requireLogin( 'changeemail-no-info' );
-
-               // This could also let someone check the current email address, so
-               // require both permissions.
-               if ( !$this->getUser()->isAllowed( 'viewmyprivateinfo' ) ) {
-                       throw new PermissionsError( 'viewmyprivateinfo' );
-               }
-
-               parent::checkExecutePermissions( $user );
-       }
-
-       protected function getFormFields() {
-               $user = $this->getUser();
-
-               $fields = [
-                       'Name' => [
-                               'type' => 'info',
-                               'label-message' => 'username',
-                               'default' => $user->getName(),
-                       ],
-                       'OldEmail' => [
-                               'type' => 'info',
-                               'label-message' => 'changeemail-oldemail',
-                               'default' => $user->getEmail() ?: $this->msg( 'changeemail-none' )->text(),
-                       ],
-                       'NewEmail' => [
-                               'type' => 'email',
-                               'label-message' => 'changeemail-newemail',
-                               'autofocus' => true,
-                               'help-message' => 'changeemail-newemail-help',
-                       ],
-               ];
-
-               if ( $this->getConfig()->get( 'RequirePasswordforEmailChange' ) ) {
-                       $fields['Password'] = [
-                               'type' => 'password',
-                               'label-message' => 'changeemail-password'
-                       ];
-               }
-
-               return $fields;
-       }
-
-       protected function getDisplayFormat() {
-               return 'ooui';
-       }
-
-       protected function alterForm( HTMLForm $form ) {
-               $form->setId( 'mw-changeemail-form' );
-               $form->setTableId( 'mw-changeemail-table' );
-               $form->setSubmitTextMsg( 'changeemail-submit' );
-               $form->addHiddenFields( $this->getRequest()->getValues( 'returnto', 'returntoquery' ) );
-
-               $form->addHeaderText( $this->msg( 'changeemail-header' )->parseAsBlock() );
-               if ( $this->getConfig()->get( 'RequirePasswordforEmailChange' ) ) {
-                       $form->addHeaderText( $this->msg( 'changeemail-passwordrequired' )->parseAsBlock() );
-               }
-       }
-
-       public function onSubmit( array $data ) {
-               $password = isset( $data['Password'] ) ? $data['Password'] : null;
-               $status = $this->attemptChange( $this->getUser(), $password, $data['NewEmail'] );
-
-               $this->status = $status;
-
-               return $status;
-       }
-
-       public function onSuccess() {
-               $request = $this->getRequest();
-
-               $returnto = $request->getVal( 'returnto' );
-               $titleObj = $returnto !== null ? Title::newFromText( $returnto ) : null;
-               if ( !$titleObj instanceof Title ) {
-                       $titleObj = Title::newMainPage();
-               }
-               $query = $request->getVal( 'returntoquery' );
-
-               if ( $this->status->value === true ) {
-                       $this->getOutput()->redirect( $titleObj->getFullURL( $query ) );
-               } elseif ( $this->status->value === 'eauth' ) {
-                       # Notify user that a confirmation email has been sent...
-                       $this->getOutput()->wrapWikiMsg( "<div class='error' style='clear: both;'>\n$1\n</div>",
-                               'eauthentsent', $this->getUser()->getName() );
-                       // just show the link to go back
-                       $this->getOutput()->addReturnTo( $titleObj, wfCgiToArray( $query ) );
-               }
-       }
-
-       /**
-        * @param User $user
-        * @param string $pass
-        * @param string $newaddr
-        * @return Status
-        */
-       private function attemptChange( User $user, $pass, $newaddr ) {
-               global $wgAuth;
-
-               if ( $newaddr != '' && !Sanitizer::validateEmail( $newaddr ) ) {
-                       return Status::newFatal( 'invalidemailaddress' );
-               }
-
-               if ( $newaddr === $user->getEmail() ) {
-                       return Status::newFatal( 'changeemail-nochange' );
-               }
-
-               $throttleInfo = LoginForm::incrementLoginThrottle( $user->getName() );
-               if ( $throttleInfo ) {
-                       $lang = $this->getLanguage();
-                       return Status::newFatal(
-                               'changeemail-throttled',
-                               $lang->formatDuration( $throttleInfo['wait'] )
-                       );
-               }
-
-               if ( $this->getConfig()->get( 'RequirePasswordforEmailChange' )
-                       && !$user->checkTemporaryPassword( $pass )
-                       && !$user->checkPassword( $pass )
-               ) {
-                       return Status::newFatal( 'wrongpassword' );
-               }
-
-               LoginForm::clearLoginThrottle( $user->getName() );
-
-               $oldaddr = $user->getEmail();
-               $status = $user->setEmailWithConfirmation( $newaddr );
-               if ( !$status->isGood() ) {
-                       return $status;
-               }
-
-               Hooks::run( 'PrefsEmailAudit', [ $user, $oldaddr, $newaddr ] );
-
-               $user->saveSettings();
-
-               $wgAuth->updateExternalDB( $user );
-
-               return $status;
-       }
-
-       public function requiresUnblock() {
-               return false;
-       }
-
-       protected function getGroupName() {
-               return 'users';
-       }
-}
diff --git a/includes/specials/pre-authmanager/SpecialChangePassword.php b/includes/specials/pre-authmanager/SpecialChangePassword.php
deleted file mode 100644 (file)
index 3955fee..0000000
+++ /dev/null
@@ -1,343 +0,0 @@
-<?php
-/**
- * Implements Special:ChangePassword
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- * @ingroup SpecialPage
- */
-
-/**
- * Let users recover their password.
- *
- * @ingroup SpecialPage
- */
-class SpecialChangePasswordPreAuthManager extends FormSpecialPage {
-       protected $mUserName;
-       protected $mDomain;
-
-       // Optional Wikitext Message to show above the password change form
-       protected $mPreTextMessage = null;
-
-       // label for old password input
-       protected $mOldPassMsg = null;
-
-       public function __construct() {
-               parent::__construct( 'ChangePassword', 'editmyprivateinfo' );
-               $this->listed( false );
-       }
-
-       public function doesWrites() {
-               return true;
-       }
-
-       /**
-        * Main execution point
-        * @param string|null $par
-        */
-       function execute( $par ) {
-               $this->getOutput()->disallowUserJs();
-
-               parent::execute( $par );
-       }
-
-       protected function checkExecutePermissions( User $user ) {
-               parent::checkExecutePermissions( $user );
-
-               if ( !$this->getRequest()->wasPosted() ) {
-                       $this->requireLogin( 'resetpass-no-info' );
-               }
-       }
-
-       /**
-        * Set a message at the top of the Change Password form
-        * @since 1.23
-        * @param Message $msg Message to parse and add to the form header
-        */
-       public function setChangeMessage( Message $msg ) {
-               $this->mPreTextMessage = $msg;
-       }
-
-       /**
-        * Set a message at the top of the Change Password form
-        * @since 1.23
-        * @param string $msg Message label for old/temp password field
-        */
-       public function setOldPasswordMessage( $msg ) {
-               $this->mOldPassMsg = $msg;
-       }
-
-       protected function getFormFields() {
-               $user = $this->getUser();
-               $request = $this->getRequest();
-
-               $oldpassMsg = $this->mOldPassMsg;
-               if ( $oldpassMsg === null ) {
-                       $oldpassMsg = $user->isLoggedIn() ? 'oldpassword' : 'resetpass-temp-password';
-               }
-
-               $fields = [
-                       'Name' => [
-                               'type' => 'info',
-                               'label-message' => 'username',
-                               'default' => $request->getVal( 'wpName', $user->getName() ),
-                       ],
-                       'Password' => [
-                               'type' => 'password',
-                               'label-message' => $oldpassMsg,
-                       ],
-                       'NewPassword' => [
-                               'type' => 'password',
-                               'label-message' => 'newpassword',
-                       ],
-                       'Retype' => [
-                               'type' => 'password',
-                               'label-message' => 'retypenew',
-                       ],
-               ];
-
-               if ( !$this->getUser()->isLoggedIn() ) {
-                       $fields['LoginOnChangeToken'] = [
-                               'type' => 'hidden',
-                               'label' => 'Change Password Token',
-                               'default' => LoginForm::getLoginToken()->toString(),
-                       ];
-               }
-
-               $extraFields = [];
-               Hooks::run( 'ChangePasswordForm', [ &$extraFields ] );
-               foreach ( $extraFields as $extra ) {
-                       list( $name, $label, $type, $default ) = $extra;
-                       $fields[$name] = [
-                               'type' => $type,
-                               'name' => $name,
-                               'label-message' => $label,
-                               'default' => $default,
-                       ];
-               }
-
-               if ( !$user->isLoggedIn() ) {
-                       $fields['Remember'] = [
-                               'type' => 'check',
-                               'label' => $this->msg( 'remembermypassword' )
-                                               ->numParams(
-                                                       ceil( $this->getConfig()->get( 'CookieExpiration' ) / ( 3600 * 24 ) )
-                                               )->text(),
-                               'default' => $request->getVal( 'wpRemember' ),
-                       ];
-               }
-
-               return $fields;
-       }
-
-       protected function alterForm( HTMLForm $form ) {
-               $form->setId( 'mw-resetpass-form' );
-               $form->setTableId( 'mw-resetpass-table' );
-               $form->setWrapperLegendMsg( 'resetpass_header' );
-               $form->setSubmitTextMsg(
-                       $this->getUser()->isLoggedIn()
-                               ? 'resetpass-submit-loggedin'
-                               : 'resetpass_submit'
-               );
-               $form->addButton( [
-                       'name' => 'wpCancel',
-                       'value' => $this->msg( 'resetpass-submit-cancel' )->text()
-               ] );
-               $form->setHeaderText( $this->msg( 'resetpass_text' )->parseAsBlock() );
-               if ( $this->mPreTextMessage instanceof Message ) {
-                       $form->addPreText( $this->mPreTextMessage->parseAsBlock() );
-               }
-               $form->addHiddenFields(
-                       $this->getRequest()->getValues( 'wpName', 'wpDomain', 'returnto', 'returntoquery' ) );
-       }
-
-       public function onSubmit( array $data ) {
-               global $wgAuth;
-
-               $request = $this->getRequest();
-
-               if ( $request->getCheck( 'wpLoginToken' ) ) {
-                       // This comes from Special:Userlogin when logging in with a temporary password
-                       return false;
-               }
-
-               if ( !$this->getUser()->isLoggedIn()
-                       && !LoginForm::getLoginToken()->match( $request->getVal( 'wpLoginOnChangeToken' ) )
-               ) {
-                       // Potential CSRF (bug 62497)
-                       return false;
-               }
-
-               if ( $request->getCheck( 'wpCancel' ) ) {
-                       $returnto = $request->getVal( 'returnto' );
-                       $titleObj = $returnto !== null ? Title::newFromText( $returnto ) : null;
-                       if ( !$titleObj instanceof Title ) {
-                               $titleObj = Title::newMainPage();
-                       }
-                       $query = $request->getVal( 'returntoquery' );
-                       $this->getOutput()->redirect( $titleObj->getFullURL( $query ) );
-
-                       return true;
-               }
-
-               $this->mUserName = $request->getVal( 'wpName', $this->getUser()->getName() );
-               $this->mDomain = $wgAuth->getDomain();
-
-               if ( !$wgAuth->allowPasswordChange() ) {
-                       throw new ErrorPageError( 'changepassword', 'resetpass_forbidden' );
-               }
-
-               $status = $this->attemptReset( $data['Password'], $data['NewPassword'], $data['Retype'] );
-
-               return $status;
-       }
-
-       public function onSuccess() {
-               if ( $this->getUser()->isLoggedIn() ) {
-                       $this->getOutput()->wrapWikiMsg(
-                               "<div class=\"successbox\">\n$1\n</div>",
-                               'changepassword-success'
-                       );
-                       $this->getOutput()->returnToMain();
-               } else {
-                       $request = $this->getRequest();
-                       LoginForm::clearLoginToken();
-                       $token = LoginForm::getLoginToken()->toString();
-                       $data = [
-                               'action' => 'submitlogin',
-                               'wpName' => $this->mUserName,
-                               'wpDomain' => $this->mDomain,
-                               'wpLoginToken' => $token,
-                               'wpPassword' => $request->getVal( 'wpNewPassword' ),
-                       ] + $request->getValues( 'wpRemember', 'returnto', 'returntoquery' );
-                       $login = new LoginForm( new DerivativeRequest( $request, $data, true ) );
-                       $login->setContext( $this->getContext() );
-                       $login->execute( null );
-               }
-       }
-
-       /**
-        * Checks the new password if it meets the requirements for passwords and set
-        * it as a current password, otherwise set the passed Status object to fatal
-        * and doesn't change anything
-        *
-        * @param string $oldpass The current (temporary) password.
-        * @param string $newpass The password to set.
-        * @param string $retype The string of the retype password field to check with newpass
-        * @return Status
-        */
-       protected function attemptReset( $oldpass, $newpass, $retype ) {
-               $isSelf = ( $this->mUserName === $this->getUser()->getName() );
-               if ( $isSelf ) {
-                       $user = $this->getUser();
-               } else {
-                       $user = User::newFromName( $this->mUserName );
-               }
-
-               if ( !$user || $user->isAnon() ) {
-                       return Status::newFatal( $this->msg( 'nosuchusershort', $this->mUserName ) );
-               }
-
-               if ( $newpass !== $retype ) {
-                       Hooks::run( 'PrefsPasswordAudit', [ $user, $newpass, 'badretype' ] );
-                       return Status::newFatal( $this->msg( 'badretype' ) );
-               }
-
-               $throttleInfo = LoginForm::incrementLoginThrottle( $this->mUserName );
-               if ( $throttleInfo ) {
-                       return Status::newFatal( $this->msg( 'changepassword-throttled' )
-                               ->durationParams( $throttleInfo['wait'] )
-                       );
-               }
-
-               // @todo Make these separate messages, since the message is written for both cases
-               if ( !$user->checkTemporaryPassword( $oldpass ) && !$user->checkPassword( $oldpass ) ) {
-                       Hooks::run( 'PrefsPasswordAudit', [ $user, $newpass, 'wrongpassword' ] );
-                       return Status::newFatal( $this->msg( 'resetpass-wrong-oldpass' ) );
-               }
-
-               // User is resetting their password to their old password
-               if ( $oldpass === $newpass ) {
-                       return Status::newFatal( $this->msg( 'resetpass-recycled' ) );
-               }
-
-               // Do AbortChangePassword after checking mOldpass, so we don't leak information
-               // by possibly aborting a new password before verifying the old password.
-               $abortMsg = 'resetpass-abort-generic';
-               if ( !Hooks::run( 'AbortChangePassword', [ $user, $oldpass, $newpass, &$abortMsg ] ) ) {
-                       Hooks::run( 'PrefsPasswordAudit', [ $user, $newpass, 'abortreset' ] );
-                       return Status::newFatal( $this->msg( $abortMsg ) );
-               }
-
-               // Please reset throttle for successful logins, thanks!
-               LoginForm::clearLoginThrottle( $this->mUserName );
-
-               try {
-                       $user->setPassword( $newpass );
-                       Hooks::run( 'PrefsPasswordAudit', [ $user, $newpass, 'success' ] );
-               } catch ( PasswordError $e ) {
-                       Hooks::run( 'PrefsPasswordAudit', [ $user, $newpass, 'error' ] );
-                       return Status::newFatal( new RawMessage( $e->getMessage() ) );
-               }
-
-               if ( $isSelf ) {
-                       // This is needed to keep the user connected since
-                       // changing the password also modifies the user's token.
-                       $remember = $this->getRequest()->getCookie( 'Token' ) !== null;
-                       $user->setCookies( null, null, $remember );
-               }
-               $user->saveSettings();
-               $this->resetPasswordExpiration( $user );
-               return Status::newGood();
-       }
-
-       public function requiresUnblock() {
-               return false;
-       }
-
-       protected function getGroupName() {
-               return 'users';
-       }
-
-       /**
-        * For resetting user password expiration, until AuthManager comes along
-        * @param User $user
-        */
-       private function resetPasswordExpiration( User $user ) {
-               global $wgPasswordExpirationDays;
-               $newExpire = null;
-               if ( $wgPasswordExpirationDays ) {
-                       $newExpire = wfTimestamp(
-                               TS_MW,
-                               time() + ( $wgPasswordExpirationDays * 24 * 3600 )
-                       );
-               }
-               // Give extensions a chance to force an expiration
-               Hooks::run( 'ResetPasswordExpiration', [ $this, &$newExpire ] );
-               $dbw = wfGetDB( DB_MASTER );
-               $dbw->update(
-                       'user',
-                       [ 'user_password_expires' => $dbw->timestampOrNull( $newExpire ) ],
-                       [ 'user_id' => $user->getId() ],
-                       __METHOD__
-               );
-       }
-
-       protected function getDisplayFormat() {
-               return 'ooui';
-       }
-}
diff --git a/includes/specials/pre-authmanager/SpecialCreateAccount.php b/includes/specials/pre-authmanager/SpecialCreateAccount.php
deleted file mode 100644 (file)
index 14f70b5..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-<?php
-/**
- * Redirect page: Special:CreateAccount --> Special:UserLogin/signup.
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- * @ingroup SpecialPage
- */
-
-/**
- * Redirect page: Special:CreateAccount --> Special:UserLogin/signup.
- * @todo FIXME: This (and the rest of the login frontend) needs to die a horrible painful death
- *
- * @ingroup SpecialPage
- */
-class SpecialCreateAccountPreAuthManager extends SpecialRedirectToSpecial {
-       function __construct() {
-               parent::__construct(
-                       'CreateAccount',
-                       'Userlogin',
-                       'signup',
-                       [ 'returnto', 'returntoquery', 'uselang' ]
-               );
-       }
-
-       public function doesWrites() {
-               return true;
-       }
-
-       // No reason to hide this link on Special:Specialpages
-       public function isListed() {
-               return true;
-       }
-
-       public function isRestricted() {
-               return !User::groupHasPermission( '*', 'createaccount' );
-       }
-
-       public function userCanExecute( User $user ) {
-               return $user->isAllowed( 'createaccount' );
-       }
-
-       protected function getGroupName() {
-               return 'login';
-       }
-}
diff --git a/includes/specials/pre-authmanager/SpecialPasswordReset.php b/includes/specials/pre-authmanager/SpecialPasswordReset.php
deleted file mode 100644 (file)
index e8719a7..0000000
+++ /dev/null
@@ -1,378 +0,0 @@
-<?php
-/**
- * Implements Special:PasswordReset
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- * @ingroup SpecialPage
- */
-
-/**
- * Special page for requesting a password reset email
- *
- * @ingroup SpecialPage
- */
-class SpecialPasswordResetPreAuthManager extends FormSpecialPage {
-       /**
-        * @var Message
-        */
-       private $email;
-
-       /**
-        * @var User
-        */
-       private $firstUser;
-
-       /**
-        * @var Status
-        */
-       private $result;
-
-       /**
-        * @var string $method Identifies which password reset field was specified by the user.
-        */
-       private $method;
-
-       public function __construct() {
-               parent::__construct( 'PasswordReset', 'editmyprivateinfo' );
-       }
-
-       public function doesWrites() {
-               return true;
-       }
-
-       public function userCanExecute( User $user ) {
-               return $this->canChangePassword( $user ) === true && parent::userCanExecute( $user );
-       }
-
-       public function checkExecutePermissions( User $user ) {
-               $error = $this->canChangePassword( $user );
-               if ( is_string( $error ) ) {
-                       throw new ErrorPageError( 'internalerror', $error );
-               } elseif ( !$error ) {
-                       throw new ErrorPageError( 'internalerror', 'resetpass_forbidden' );
-               }
-
-               parent::checkExecutePermissions( $user );
-       }
-
-       protected function getFormFields() {
-               global $wgAuth;
-               $resetRoutes = $this->getConfig()->get( 'PasswordResetRoutes' );
-               $a = [];
-               if ( isset( $resetRoutes['username'] ) && $resetRoutes['username'] ) {
-                       $a['Username'] = [
-                               'type' => 'text',
-                               'label-message' => 'passwordreset-username',
-                       ];
-
-                       if ( $this->getUser()->isLoggedIn() ) {
-                               $a['Username']['default'] = $this->getUser()->getName();
-                       }
-               }
-
-               if ( isset( $resetRoutes['email'] ) && $resetRoutes['email'] ) {
-                       $a['Email'] = [
-                               'type' => 'email',
-                               'label-message' => 'passwordreset-email',
-                       ];
-               }
-
-               if ( isset( $resetRoutes['domain'] ) && $resetRoutes['domain'] ) {
-                       $domains = $wgAuth->domainList();
-                       $a['Domain'] = [
-                               'type' => 'select',
-                               'options' => $domains,
-                               'label-message' => 'passwordreset-domain',
-                       ];
-               }
-
-               if ( $this->getUser()->isAllowed( 'passwordreset' ) ) {
-                       $a['Capture'] = [
-                               'type' => 'check',
-                               'label-message' => 'passwordreset-capture',
-                               'help-message' => 'passwordreset-capture-help',
-                       ];
-               }
-
-               return $a;
-       }
-
-       protected function getDisplayFormat() {
-               return 'ooui';
-       }
-
-       public function alterForm( HTMLForm $form ) {
-               $resetRoutes = $this->getConfig()->get( 'PasswordResetRoutes' );
-
-               $form->addHiddenFields( $this->getRequest()->getValues( 'returnto', 'returntoquery' ) );
-
-               $i = 0;
-               if ( isset( $resetRoutes['username'] ) && $resetRoutes['username'] ) {
-                       $i++;
-               }
-               if ( isset( $resetRoutes['email'] ) && $resetRoutes['email'] ) {
-                       $i++;
-               }
-               if ( isset( $resetRoutes['domain'] ) && $resetRoutes['domain'] ) {
-                       $i++;
-               }
-
-               $message = ( $i > 1 ) ? 'passwordreset-text-many' : 'passwordreset-text-one';
-
-               $form->setHeaderText( $this->msg( $message, $i )->parseAsBlock() );
-               $form->setSubmitTextMsg( 'mailmypassword' );
-       }
-
-       /**
-        * Process the form.  At this point we know that the user passes all the criteria in
-        * userCanExecute(), and if the data array contains 'Username', etc, then Username
-        * resets are allowed.
-        * @param array $data
-        * @throws MWException
-        * @throws ThrottledError|PermissionsError
-        * @return bool|array
-        */
-       public function onSubmit( array $data ) {
-               global $wgAuth, $wgMinimalPasswordLength;
-
-               if ( isset( $data['Domain'] ) ) {
-                       if ( $wgAuth->validDomain( $data['Domain'] ) ) {
-                               $wgAuth->setDomain( $data['Domain'] );
-                       } else {
-                               $wgAuth->setDomain( 'invaliddomain' );
-                       }
-               }
-
-               if ( isset( $data['Capture'] ) && !$this->getUser()->isAllowed( 'passwordreset' ) ) {
-                       // The user knows they don't have the passwordreset permission,
-                       // but they tried to spoof the form. That's naughty
-                       throw new PermissionsError( 'passwordreset' );
-               }
-
-               /**
-                * @var $firstUser User
-                * @var $users User[]
-                */
-
-               if ( isset( $data['Username'] ) && $data['Username'] !== '' ) {
-                       $method = 'username';
-                       $users = [ User::newFromName( $data['Username'] ) ];
-               } elseif ( isset( $data['Email'] )
-                       && $data['Email'] !== ''
-                       && Sanitizer::validateEmail( $data['Email'] )
-               ) {
-                       $method = 'email';
-                       $res = wfGetDB( DB_SLAVE )->select(
-                               'user',
-                               User::selectFields(),
-                               [ 'user_email' => $data['Email'] ],
-                               __METHOD__
-                       );
-
-                       if ( $res ) {
-                               $users = [];
-
-                               foreach ( $res as $row ) {
-                                       $users[] = User::newFromRow( $row );
-                               }
-                       } else {
-                               // Some sort of database error, probably unreachable
-                               throw new MWException( 'Unknown database error in ' . __METHOD__ );
-                       }
-               } else {
-                       // The user didn't supply any data
-                       return false;
-               }
-
-               // Check for hooks (captcha etc), and allow them to modify the users list
-               $error = [];
-               if ( !Hooks::run( 'SpecialPasswordResetOnSubmit', [ &$users, $data, &$error ] ) ) {
-                       return [ $error ];
-               }
-
-               $this->method = $method;
-
-               if ( count( $users ) == 0 ) {
-                       if ( $method == 'email' ) {
-                               // Don't reveal whether or not an email address is in use
-                               return true;
-                       } else {
-                               return [ 'noname' ];
-                       }
-               }
-
-               $firstUser = $users[0];
-
-               if ( !$firstUser instanceof User || !$firstUser->getId() ) {
-                       // Don't parse username as wikitext (bug 65501)
-                       return [ [ 'nosuchuser', wfEscapeWikiText( $data['Username'] ) ] ];
-               }
-
-               // Check against the rate limiter
-               if ( $this->getUser()->pingLimiter( 'mailpassword' ) ) {
-                       throw new ThrottledError;
-               }
-
-               // Check against password throttle
-               foreach ( $users as $user ) {
-                       if ( $user->isPasswordReminderThrottled() ) {
-
-                               # Round the time in hours to 3 d.p., in case someone is specifying
-                               # minutes or seconds.
-                               return [ [
-                                       'throttled-mailpassword',
-                                       round( $this->getConfig()->get( 'PasswordReminderResendTime' ), 3 )
-                               ] ];
-                       }
-               }
-
-               // All the users will have the same email address
-               if ( $firstUser->getEmail() == '' ) {
-                       // This won't be reachable from the email route, so safe to expose the username
-                       return [ [ 'noemail', wfEscapeWikiText( $firstUser->getName() ) ] ];
-               }
-
-               // We need to have a valid IP address for the hook, but per bug 18347, we should
-               // send the user's name if they're logged in.
-               $ip = $this->getRequest()->getIP();
-               if ( !$ip ) {
-                       return [ 'badipaddress' ];
-               }
-               $caller = $this->getUser();
-               Hooks::run( 'User::mailPasswordInternal', [ &$caller, &$ip, &$firstUser ] );
-               $username = $caller->getName();
-               $msg = IP::isValid( $username )
-                       ? 'passwordreset-emailtext-ip'
-                       : 'passwordreset-emailtext-user';
-
-               // Send in the user's language; which should hopefully be the same
-               $userLanguage = $firstUser->getOption( 'language' );
-
-               $passwords = [];
-               foreach ( $users as $user ) {
-                       $password = PasswordFactory::generateRandomPasswordString( $wgMinimalPasswordLength );
-                       $user->setNewpassword( $password );
-                       $user->saveSettings();
-                       $passwords[] = $this->msg( 'passwordreset-emailelement', $user->getName(), $password )
-                               ->inLanguage( $userLanguage )->text(); // We'll escape the whole thing later
-               }
-               $passwordBlock = implode( "\n\n", $passwords );
-
-               $this->email = $this->msg( $msg )->inLanguage( $userLanguage );
-               $this->email->params(
-                       $username,
-                       $passwordBlock,
-                       count( $passwords ),
-                       '<' . Title::newMainPage()->getCanonicalURL() . '>',
-                       round( $this->getConfig()->get( 'NewPasswordExpiry' ) / 86400 )
-               );
-
-               $title = $this->msg( 'passwordreset-emailtitle' )->inLanguage( $userLanguage );
-
-               $this->result = $firstUser->sendMail( $title->text(), $this->email->text() );
-
-               if ( isset( $data['Capture'] ) && $data['Capture'] ) {
-                       // Save the user, will be used if an error occurs when sending the email
-                       $this->firstUser = $firstUser;
-               } else {
-                       // Blank the email if the user is not supposed to see it
-                       $this->email = null;
-               }
-
-               if ( $this->result->isGood() ) {
-                       return true;
-               } elseif ( isset( $data['Capture'] ) && $data['Capture'] ) {
-                       // The email didn't send, but maybe they knew that and that's why they captured it
-                       return true;
-               } else {
-                       // @todo FIXME: The email wasn't sent, but we have already set
-                       // the password throttle timestamp, so they won't be able to try
-                       // again until it expires...  :(
-                       return [ [ 'mailerror', $this->result->getMessage() ] ];
-               }
-       }
-
-       public function onSuccess() {
-               if ( $this->getUser()->isAllowed( 'passwordreset' ) && $this->email != null ) {
-                       // @todo Logging
-
-                       if ( $this->result->isGood() ) {
-                               $this->getOutput()->addWikiMsg( 'passwordreset-emailsent-capture' );
-                       } else {
-                               $this->getOutput()->addWikiMsg( 'passwordreset-emailerror-capture',
-                                       $this->result->getMessage(), $this->firstUser->getName() );
-                       }
-
-                       $this->getOutput()->addHTML( Html::rawElement( 'pre', [], $this->email->escaped() ) );
-               }
-
-               if ( $this->method === 'email' ) {
-                       $this->getOutput()->addWikiMsg( 'passwordreset-emailsentemail' );
-               } else {
-                       $this->getOutput()->addWikiMsg( 'passwordreset-emailsentusername' );
-               }
-
-               $this->getOutput()->returnToMain();
-       }
-
-       protected function canChangePassword( User $user ) {
-               global $wgAuth;
-               $resetRoutes = $this->getConfig()->get( 'PasswordResetRoutes' );
-
-               // Maybe password resets are disabled, or there are no allowable routes
-               if ( !is_array( $resetRoutes ) ||
-                       !in_array( true, array_values( $resetRoutes ) )
-               ) {
-                       return 'passwordreset-disabled';
-               }
-
-               // Maybe the external auth plugin won't allow local password changes
-               if ( !$wgAuth->allowPasswordChange() ) {
-                       return 'resetpass_forbidden';
-               }
-
-               // Maybe email features have been disabled
-               if ( !$this->getConfig()->get( 'EnableEmail' ) ) {
-                       return 'passwordreset-emaildisabled';
-               }
-
-               // Maybe the user is blocked (check this here rather than relying on the parent
-               // method as we have a more specific error message to use here
-               if ( $user->isBlocked() ) {
-                       return 'blocked-mailpassword';
-               }
-
-               return true;
-       }
-
-       /**
-        * Hide the password reset page if resets are disabled.
-        * @return bool
-        */
-       function isListed() {
-               if ( $this->canChangePassword( $this->getUser() ) === true ) {
-                       return parent::isListed();
-               }
-
-               return false;
-       }
-
-       protected function getGroupName() {
-               return 'users';
-       }
-}
diff --git a/includes/specials/pre-authmanager/SpecialUserlogin.php b/includes/specials/pre-authmanager/SpecialUserlogin.php
deleted file mode 100644 (file)
index 09132f2..0000000
+++ /dev/null
@@ -1,1847 +0,0 @@
-<?php
-/**
- * Implements Special:UserLogin
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- * @ingroup SpecialPage
- */
-use MediaWiki\Logger\LoggerFactory;
-use Psr\Log\LogLevel;
-use MediaWiki\Session\SessionManager;
-
-/**
- * Implements Special:UserLogin
- *
- * @ingroup SpecialPage
- */
-class LoginFormPreAuthManager extends SpecialPage {
-       const SUCCESS = 0;
-       const NO_NAME = 1;
-       const ILLEGAL = 2;
-       const WRONG_PLUGIN_PASS = 3;
-       const NOT_EXISTS = 4;
-       const WRONG_PASS = 5;
-       const EMPTY_PASS = 6;
-       const RESET_PASS = 7;
-       const ABORTED = 8;
-       const CREATE_BLOCKED = 9;
-       const THROTTLED = 10;
-       const USER_BLOCKED = 11;
-       const NEED_TOKEN = 12;
-       const WRONG_TOKEN = 13;
-       const USER_MIGRATED = 14;
-
-       public static $statusCodes = [
-               self::SUCCESS => 'success',
-               self::NO_NAME => 'no_name',
-               self::ILLEGAL => 'illegal',
-               self::WRONG_PLUGIN_PASS => 'wrong_plugin_pass',
-               self::NOT_EXISTS => 'not_exists',
-               self::WRONG_PASS => 'wrong_pass',
-               self::EMPTY_PASS => 'empty_pass',
-               self::RESET_PASS => 'reset_pass',
-               self::ABORTED => 'aborted',
-               self::CREATE_BLOCKED => 'create_blocked',
-               self::THROTTLED => 'throttled',
-               self::USER_BLOCKED => 'user_blocked',
-               self::NEED_TOKEN => 'need_token',
-               self::WRONG_TOKEN => 'wrong_token',
-               self::USER_MIGRATED => 'user_migrated',
-       ];
-
-       /**
-        * Valid error and warning messages
-        *
-        * Special:Userlogin can show an error or warning message on the form when
-        * coming from another page. This is done via the ?error= or ?warning= GET
-        * parameters.
-        *
-        * This array is the list of valid message keys. All other values will be
-        * ignored.
-        *
-        * @since 1.24
-        * @var string[]
-        */
-       public static $validErrorMessages = [
-               'exception-nologin-text',
-               'watchlistanontext',
-               'changeemail-no-info',
-               'resetpass-no-info',
-               'confirmemail_needlogin',
-               'prefsnologintext2',
-       ];
-
-       public $mAbortLoginErrorMsg = null;
-       /**
-        * @var int How many seconds user is throttled for
-        * @since 1.27
-        */
-       public $mThrottleWait = '?';
-
-       protected $mUsername;
-       protected $mPassword;
-       protected $mRetype;
-       protected $mReturnTo;
-       protected $mCookieCheck;
-       protected $mPosted;
-       protected $mAction;
-       protected $mCreateaccount;
-       protected $mCreateaccountMail;
-       protected $mLoginattempt;
-       protected $mRemember;
-       protected $mEmail;
-       protected $mDomain;
-       protected $mLanguage;
-       protected $mSkipCookieCheck;
-       protected $mReturnToQuery;
-       protected $mToken;
-       protected $mStickHTTPS;
-       protected $mType;
-       protected $mReason;
-       protected $mRealName;
-       protected $mEntryError = '';
-       protected $mEntryErrorType = 'error';
-
-       private $mTempPasswordUsed;
-       private $mLoaded = false;
-       private $mSecureLoginUrl;
-
-       /** @var WebRequest */
-       private $mOverrideRequest = null;
-
-       /** @var WebRequest Effective request; set at the beginning of load */
-       private $mRequest = null;
-
-       /**
-        * @param WebRequest $request
-        */
-       public function __construct( $request = null ) {
-               global $wgUseMediaWikiUIEverywhere;
-               parent::__construct( 'Userlogin' );
-
-               $this->mOverrideRequest = $request;
-               // Override UseMediaWikiEverywhere to true, to force login and create form to use mw ui
-               $wgUseMediaWikiUIEverywhere = true;
-       }
-
-       public function doesWrites() {
-               return true;
-       }
-
-       /**
-        * Returns an array of all valid error messages.
-        *
-        * @return array
-        */
-       public static function getValidErrorMessages() {
-               static $messages = null;
-               if ( !$messages ) {
-                       $messages = self::$validErrorMessages;
-                       Hooks::run( 'LoginFormValidErrorMessages', [ &$messages ] );
-               }
-
-               return $messages;
-       }
-
-       /**
-        * Loader
-        */
-       function load() {
-               global $wgAuth, $wgHiddenPrefs, $wgEnableEmail;
-
-               if ( $this->mLoaded ) {
-                       return;
-               }
-               $this->mLoaded = true;
-
-               if ( $this->mOverrideRequest === null ) {
-                       $request = $this->getRequest();
-               } else {
-                       $request = $this->mOverrideRequest;
-               }
-               $this->mRequest = $request;
-
-               $this->mType = $request->getText( 'type' );
-               $this->mUsername = $request->getText( 'wpName' );
-               $this->mPassword = $request->getText( 'wpPassword' );
-               $this->mRetype = $request->getText( 'wpRetype' );
-               $this->mDomain = $request->getText( 'wpDomain' );
-               $this->mReason = $request->getText( 'wpReason' );
-               $this->mCookieCheck = $request->getVal( 'wpCookieCheck' );
-               $this->mPosted = $request->wasPosted();
-               $this->mCreateaccountMail = $request->getCheck( 'wpCreateaccountMail' )
-                       && $wgEnableEmail;
-               $this->mCreateaccount = $request->getCheck( 'wpCreateaccount' ) && !$this->mCreateaccountMail;
-               $this->mLoginattempt = $request->getCheck( 'wpLoginattempt' );
-               $this->mAction = $request->getVal( 'action' );
-               $this->mRemember = $request->getCheck( 'wpRemember' );
-               $this->mFromHTTP = $request->getBool( 'fromhttp', false )
-                       || $request->getBool( 'wpFromhttp', false );
-               $this->mStickHTTPS = ( !$this->mFromHTTP && $request->getProtocol() === 'https' )
-                       || $request->getBool( 'wpForceHttps', false );
-               $this->mLanguage = $request->getText( 'uselang' );
-               $this->mSkipCookieCheck = $request->getCheck( 'wpSkipCookieCheck' );
-               $this->mToken = $this->mType == 'signup'
-                       ? $request->getVal( 'wpCreateaccountToken' )
-                       : $request->getVal( 'wpLoginToken' );
-               $this->mReturnTo = $request->getVal( 'returnto', '' );
-               $this->mReturnToQuery = $request->getVal( 'returntoquery', '' );
-
-               // Show an error or warning passed on from a previous page
-               $entryError = $this->msg( $request->getVal( 'error', '' ) );
-               $entryWarning = $this->msg( $request->getVal( 'warning', '' ) );
-               // bc: provide login link as a parameter for messages where the translation
-               // was not updated
-               $loginreqlink = Linker::linkKnown(
-                       $this->getPageTitle(),
-                       $this->msg( 'loginreqlink' )->escaped(),
-                       [],
-                       [
-                               'returnto' => $this->mReturnTo,
-                               'returntoquery' => $this->mReturnToQuery,
-                               'uselang' => $this->mLanguage,
-                               'fromhttp' => $this->mFromHTTP ? '1' : '0',
-                       ]
-               );
-
-               // Only show valid error or warning messages.
-               if ( $entryError->exists()
-                       && in_array( $entryError->getKey(), self::getValidErrorMessages() )
-               ) {
-                       $this->mEntryErrorType = 'error';
-                       $this->mEntryError = $entryError->rawParams( $loginreqlink )->parse();
-
-               } elseif ( $entryWarning->exists()
-                       && in_array( $entryWarning->getKey(), self::getValidErrorMessages() )
-               ) {
-                       $this->mEntryErrorType = 'warning';
-                       $this->mEntryError = $entryWarning->rawParams( $loginreqlink )->parse();
-               }
-
-               if ( $wgEnableEmail ) {
-                       $this->mEmail = $request->getText( 'wpEmail' );
-               } else {
-                       $this->mEmail = '';
-               }
-               if ( !in_array( 'realname', $wgHiddenPrefs ) ) {
-                       $this->mRealName = $request->getText( 'wpRealName' );
-               } else {
-                       $this->mRealName = '';
-               }
-
-               if ( !$wgAuth->validDomain( $this->mDomain ) ) {
-                       $this->mDomain = $wgAuth->getDomain();
-               }
-               $wgAuth->setDomain( $this->mDomain );
-
-               # 1. When switching accounts, it sucks to get automatically logged out
-               # 2. Do not return to PasswordReset after a successful password change
-               #    but goto Wiki start page (Main_Page) instead ( bug 33997 )
-               $returnToTitle = Title::newFromText( $this->mReturnTo );
-               if ( is_object( $returnToTitle )
-                       && ( $returnToTitle->isSpecial( 'Userlogout' )
-                               || $returnToTitle->isSpecial( 'PasswordReset' ) )
-               ) {
-                       $this->mReturnTo = '';
-                       $this->mReturnToQuery = '';
-               }
-       }
-
-       function getDescription() {
-               if ( $this->mType === 'signup' ) {
-                       return $this->msg( 'createaccount' )->text();
-               } else {
-                       return $this->msg( 'login' )->text();
-               }
-       }
-
-       /**
-        * @param string|null $subPage
-        */
-       public function execute( $subPage ) {
-               // Make sure session is persisted
-               $session = SessionManager::getGlobalSession();
-               $session->persist();
-
-               $this->load();
-
-               // Check for [[Special:Userlogin/signup]]. This affects form display and
-               // page title.
-               if ( $subPage == 'signup' ) {
-                       $this->mType = 'signup';
-               }
-               $this->setHeaders();
-
-               // Make sure it's possible to log in
-               if ( $this->mType !== 'signup' && !$session->canSetUser() ) {
-                       throw new ErrorPageError(
-                               'cannotloginnow-title',
-                               'cannotloginnow-text',
-                               [
-                                       $session->getProvider()->describe( RequestContext::getMain()->getLanguage() )
-                               ]
-                       );
-               }
-
-               /**
-                * In the case where the user is already logged in, and was redirected to
-                * the login form from a page that requires login, do not show the login
-                * page. The use case scenario for this is when a user opens a large number
-                * of tabs, is redirected to the login page on all of them, and then logs
-                * in on one, expecting all the others to work properly.
-                *
-                * However, do show the form if it was visited intentionally (no 'returnto'
-                * is present). People who often switch between several accounts have grown
-                * accustomed to this behavior.
-                */
-               if (
-                       $this->mType !== 'signup' &&
-                       !$this->mPosted &&
-                       $this->getUser()->isLoggedIn() &&
-                       ( $this->mReturnTo !== '' || $this->mReturnToQuery !== '' )
-               ) {
-                       $this->successfulLogin();
-               }
-
-               // If logging in and not on HTTPS, either redirect to it or offer a link.
-               global $wgSecureLogin;
-               if ( $this->mRequest->getProtocol() !== 'https' ) {
-                       $title = $this->getFullTitle();
-                       $query = [
-                               'returnto' => $this->mReturnTo !== '' ? $this->mReturnTo : null,
-                               'returntoquery' => $this->mReturnToQuery !== '' ?
-                                       $this->mReturnToQuery : null,
-                               'title' => null,
-                               ( $this->mEntryErrorType === 'error' ? 'error' : 'warning' ) => $this->mEntryError,
-                       ] + $this->mRequest->getQueryValues();
-                       $url = $title->getFullURL( $query, false, PROTO_HTTPS );
-                       if ( $wgSecureLogin
-                               && wfCanIPUseHTTPS( $this->getRequest()->getIP() )
-                               && !$this->mFromHTTP ) // Avoid infinite redirect
-                       {
-                               $url = wfAppendQuery( $url, 'fromhttp=1' );
-                               $this->getOutput()->redirect( $url );
-                               // Since we only do this redir to change proto, always vary
-                               $this->getOutput()->addVaryHeader( 'X-Forwarded-Proto' );
-
-                               return;
-                       } else {
-                               // A wiki without HTTPS login support should set $wgServer to
-                               // http://somehost, in which case the secure URL generated
-                               // above won't actually start with https://
-                               if ( substr( $url, 0, 8 ) === 'https://' ) {
-                                       $this->mSecureLoginUrl = $url;
-                               }
-                       }
-               }
-
-               if ( !is_null( $this->mCookieCheck ) ) {
-                       $this->onCookieRedirectCheck( $this->mCookieCheck );
-
-                       return;
-               } elseif ( $this->mPosted ) {
-                       if ( $this->mCreateaccount ) {
-                               $this->addNewAccount();
-
-                               return;
-                       } elseif ( $this->mCreateaccountMail ) {
-                               $this->addNewAccountMailPassword();
-
-                               return;
-                       } elseif ( ( 'submitlogin' == $this->mAction ) || $this->mLoginattempt ) {
-                               $this->processLogin();
-
-                               return;
-                       }
-               }
-               $this->mainLoginForm( $this->mEntryError, $this->mEntryErrorType );
-       }
-
-       /**
-        * @private
-        */
-       function addNewAccountMailPassword() {
-               if ( $this->mEmail == '' ) {
-                       $this->mainLoginForm( $this->msg( 'noemailcreate' )->escaped() );
-
-                       return;
-               }
-
-               $status = $this->addNewAccountInternal();
-               LoggerFactory::getInstance( 'authmanager' )->info(
-                       'Account creation attempt with mailed password',
-                       [ 'event' => 'accountcreation', 'status' => $status ]
-               );
-               if ( !$status->isGood() ) {
-                       $error = $status->getMessage();
-                       $this->mainLoginForm( $error->toString() );
-
-                       return;
-               }
-
-               /** @var User $u */
-               $u = $status->getValue();
-
-               // Wipe the initial password and mail a temporary one
-               $u->setPassword( null );
-               $u->saveSettings();
-               $result = $this->mailPasswordInternal( $u, false, 'createaccount-title', 'createaccount-text' );
-
-               Hooks::run( 'AddNewAccount', [ $u, true ] );
-               $u->addNewUserLogEntry( 'byemail', $this->mReason );
-
-               $out = $this->getOutput();
-               $out->setPageTitle( $this->msg( 'accmailtitle' ) );
-
-               if ( !$result->isGood() ) {
-                       $this->mainLoginForm( $this->msg( 'mailerror', $result->getWikiText() )->text() );
-               } else {
-                       $out->addWikiMsg( 'accmailtext', $u->getName(), $u->getEmail() );
-                       $this->executeReturnTo( 'success' );
-               }
-       }
-
-       /**
-        * @private
-        * @return bool
-        */
-       function addNewAccount() {
-               global $wgContLang, $wgUser, $wgEmailAuthentication, $wgLoginLanguageSelector;
-
-               # Create the account and abort if there's a problem doing so
-               $status = $this->addNewAccountInternal();
-               LoggerFactory::getInstance( 'authmanager' )->info( 'Account creation attempt', [
-                       'event' => 'accountcreation',
-                       'status' => $status,
-               ] );
-
-               if ( !$status->isGood() ) {
-                       $error = $status->getMessage();
-                       $this->mainLoginForm( $error->toString() );
-
-                       return false;
-               }
-
-               $u = $status->getValue();
-
-               # Only save preferences if the user is not creating an account for someone else.
-               if ( $this->getUser()->isAnon() ) {
-                       # If we showed up language selection links, and one was in use, be
-                       # smart (and sensible) and save that language as the user's preference
-                       if ( $wgLoginLanguageSelector && $this->mLanguage ) {
-                               $u->setOption( 'language', $this->mLanguage );
-                       } else {
-
-                               # Otherwise the user's language preference defaults to $wgContLang,
-                               # but it may be better to set it to their preferred $wgContLang variant,
-                               # based on browser preferences or URL parameters.
-                               $u->setOption( 'language', $wgContLang->getPreferredVariant() );
-                       }
-                       if ( $wgContLang->hasVariants() ) {
-                               $u->setOption( 'variant', $wgContLang->getPreferredVariant() );
-                       }
-               }
-
-               $out = $this->getOutput();
-
-               # Send out an email authentication message if needed
-               if ( $wgEmailAuthentication && Sanitizer::validateEmail( $u->getEmail() ) ) {
-                       $status = $u->sendConfirmationMail();
-                       if ( $status->isGood() ) {
-                               $out->addWikiMsg( 'confirmemail_oncreate' );
-                       } else {
-                               $out->addWikiText( $status->getWikiText( 'confirmemail_sendfailed' ) );
-                       }
-               }
-
-               # Save settings (including confirmation token)
-               $u->saveSettings();
-
-               # If not logged in, assume the new account as the current one and set
-               # session cookies then show a "welcome" message or a "need cookies"
-               # message as needed
-               if ( $this->getUser()->isAnon() ) {
-                       $u->setCookies();
-                       $wgUser = $u;
-                       // This should set it for OutputPage and the Skin
-                       // which is needed or the personal links will be
-                       // wrong.
-                       $this->getContext()->setUser( $u );
-                       Hooks::run( 'AddNewAccount', [ $u, false ] );
-                       $u->addNewUserLogEntry( 'create' );
-                       if ( $this->hasSessionCookie() ) {
-                               $this->successfulCreation();
-                       } else {
-                               $this->cookieRedirectCheck( 'new' );
-                       }
-               } else {
-                       # Confirm that the account was created
-                       $out->setPageTitle( $this->msg( 'accountcreated' ) );
-                       $out->addWikiMsg( 'accountcreatedtext', $u->getName() );
-                       $out->addReturnTo( $this->getPageTitle() );
-                       Hooks::run( 'AddNewAccount', [ $u, false ] );
-                       $u->addNewUserLogEntry( 'create2', $this->mReason );
-               }
-
-               return true;
-       }
-
-       /**
-        * Make a new user account using the loaded data.
-        * @private
-        * @throws PermissionsError|ReadOnlyError
-        * @return Status
-        */
-       public function addNewAccountInternal() {
-               global $wgAuth, $wgAccountCreationThrottle, $wgEmailConfirmToEdit;
-
-               // If the user passes an invalid domain, something is fishy
-               if ( !$wgAuth->validDomain( $this->mDomain ) ) {
-                       return Status::newFatal( 'wrongpassword' );
-               }
-
-               // If we are not allowing users to login locally, we should be checking
-               // to see if the user is actually able to authenticate to the authenti-
-               // cation server before they create an account (otherwise, they can
-               // create a local account and login as any domain user). We only need
-               // to check this for domains that aren't local.
-               if ( 'local' != $this->mDomain && $this->mDomain != '' ) {
-                       if (
-                               !$wgAuth->canCreateAccounts() &&
-                               (
-                                       !$wgAuth->userExists( $this->mUsername ) ||
-                                       !$wgAuth->authenticate( $this->mUsername, $this->mPassword )
-                               )
-                       ) {
-                               return Status::newFatal( 'wrongpassword' );
-                       }
-               }
-
-               if ( wfReadOnly() ) {
-                       throw new ReadOnlyError;
-               }
-
-               # Request forgery checks.
-               $token = self::getCreateaccountToken();
-               if ( $token->wasNew() ) {
-                       return Status::newFatal( 'nocookiesfornew' );
-               }
-
-               # The user didn't pass a createaccount token
-               if ( !$this->mToken ) {
-                       return Status::newFatal( 'sessionfailure' );
-               }
-
-               # Validate the createaccount token
-               if ( !$token->match( $this->mToken ) ) {
-                       return Status::newFatal( 'sessionfailure' );
-               }
-
-               # Check permissions
-               $currentUser = $this->getUser();
-               $creationBlock = $currentUser->isBlockedFromCreateAccount();
-               if ( !$currentUser->isAllowed( 'createaccount' ) ) {
-                       throw new PermissionsError( 'createaccount' );
-               } elseif ( $creationBlock instanceof Block ) {
-                       // Throws an ErrorPageError.
-                       $this->userBlockedMessage( $creationBlock );
-
-                       // This should never be reached.
-                       return false;
-               }
-
-               # Include checks that will include GlobalBlocking (Bug 38333)
-               $permErrors = $this->getPageTitle()->getUserPermissionsErrors(
-                       'createaccount',
-                       $currentUser,
-                       true
-               );
-
-               if ( count( $permErrors ) ) {
-                       throw new PermissionsError( 'createaccount', $permErrors );
-               }
-
-               $ip = $this->getRequest()->getIP();
-               if ( $currentUser->isDnsBlacklisted( $ip, true /* check $wgProxyWhitelist */ ) ) {
-                       return Status::newFatal( 'sorbs_create_account_reason' );
-               }
-
-               # Now create a dummy user ($u) and check if it is valid
-               $u = User::newFromName( $this->mUsername, 'creatable' );
-               if ( !$u ) {
-                       return Status::newFatal( 'noname' );
-               }
-
-               $cache = ObjectCache::getLocalClusterInstance();
-               # Make sure the user does not exist already
-               $lock = $cache->getScopedLock( $cache->makeGlobalKey( 'account', md5( $this->mUsername ) ) );
-               if ( !$lock ) {
-                       return Status::newFatal( 'usernameinprogress' );
-               } elseif ( $u->idForName( User::READ_LOCKING ) ) {
-                       return Status::newFatal( 'userexists' );
-               }
-
-               if ( $this->mCreateaccountMail ) {
-                       # do not force a password for account creation by email
-                       # set invalid password, it will be replaced later by a random generated password
-                       $this->mPassword = null;
-               } else {
-                       if ( $this->mPassword !== $this->mRetype ) {
-                               return Status::newFatal( 'badretype' );
-                       }
-
-                       # check for password validity, return a fatal Status if invalid
-                       $validity = $u->checkPasswordValidity( $this->mPassword, 'create' );
-                       if ( !$validity->isGood() ) {
-                               $validity->ok = false; // make sure this Status is fatal
-                               return $validity;
-                       }
-               }
-
-               # if you need a confirmed email address to edit, then obviously you
-               # need an email address.
-               if ( $wgEmailConfirmToEdit && strval( $this->mEmail ) === '' ) {
-                       return Status::newFatal( 'noemailtitle' );
-               }
-
-               if ( strval( $this->mEmail ) !== '' && !Sanitizer::validateEmail( $this->mEmail ) ) {
-                       return Status::newFatal( 'invalidemailaddress' );
-               }
-
-               # Set some additional data so the AbortNewAccount hook can be used for
-               # more than just username validation
-               $u->setEmail( $this->mEmail );
-               $u->setRealName( $this->mRealName );
-
-               $abortError = '';
-               $abortStatus = null;
-               if ( !Hooks::run( 'AbortNewAccount', [ $u, &$abortError, &$abortStatus ] ) ) {
-                       // Hook point to add extra creation throttles and blocks
-                       wfDebug( "LoginForm::addNewAccountInternal: a hook blocked creation\n" );
-                       if ( $abortStatus === null ) {
-                               // Report back the old string as a raw message status.
-                               // This will report the error back as 'createaccount-hook-aborted'
-                               // with the given string as the message.
-                               // To return a different error code, return a Status object.
-                               $abortError = new Message( 'createaccount-hook-aborted', [ $abortError ] );
-                               $abortError->text();
-
-                               return Status::newFatal( $abortError );
-                       } else {
-                               // For MediaWiki 1.23+ and updated hooks, return the Status object
-                               // returned from the hook.
-                               return $abortStatus;
-                       }
-               }
-
-               // Hook point to check for exempt from account creation throttle
-               if ( !Hooks::run( 'ExemptFromAccountCreationThrottle', [ $ip ] ) ) {
-                       wfDebug( "LoginForm::exemptFromAccountCreationThrottle: a hook " .
-                               "allowed account creation w/o throttle\n" );
-               } else {
-                       if ( ( $wgAccountCreationThrottle && $currentUser->isPingLimitable() ) ) {
-                               $key = wfGlobalCacheKey( 'acctcreate', 'ip', $ip );
-                               $value = $cache->get( $key );
-                               if ( !$value ) {
-                                       $cache->set( $key, 0, $cache::TTL_DAY );
-                               }
-                               if ( $value >= $wgAccountCreationThrottle ) {
-                                       return Status::newFatal( 'acct_creation_throttle_hit', $wgAccountCreationThrottle );
-                               }
-                               $cache->incr( $key );
-                       }
-               }
-
-               if ( !$wgAuth->addUser( $u, $this->mPassword, $this->mEmail, $this->mRealName ) ) {
-                       return Status::newFatal( 'externaldberror' );
-               }
-
-               self::clearCreateaccountToken();
-
-               return $this->initUser( $u, false );
-       }
-
-       /**
-        * Actually add a user to the database.
-        * Give it a User object that has been initialised with a name.
-        *
-        * @param User $u
-        * @param bool $autocreate True if this is an autocreation via auth plugin
-        * @return Status Status object, with the User object in the value member on success
-        * @private
-        */
-       function initUser( $u, $autocreate ) {
-               global $wgAuth;
-
-               $status = $u->addToDatabase();
-               if ( !$status->isOK() ) {
-                       return $status;
-               }
-
-               if ( $wgAuth->allowPasswordChange() ) {
-                       $u->setPassword( $this->mPassword );
-               }
-
-               $u->setEmail( $this->mEmail );
-               $u->setRealName( $this->mRealName );
-               $u->setToken();
-
-               Hooks::run( 'LocalUserCreated', [ $u, $autocreate ] );
-               $oldUser = $u;
-               $wgAuth->initUser( $u, $autocreate );
-               if ( $oldUser !== $u ) {
-                       wfWarn( get_class( $wgAuth ) . '::initUser() replaced the user object' );
-               }
-
-               $u->saveSettings();
-
-               // Update user count
-               DeferredUpdates::addUpdate( new SiteStatsUpdate( 0, 0, 0, 0, 1 ) );
-
-               // Watch user's userpage and talk page
-               $u->addWatch( $u->getUserPage(), User::IGNORE_USER_RIGHTS );
-
-               return Status::newGood( $u );
-       }
-
-       /**
-        * Internally authenticate the login request.
-        *
-        * This may create a local account as a side effect if the
-        * authentication plugin allows transparent local account
-        * creation.
-        * @return int
-        */
-       public function authenticateUserData() {
-               global $wgUser, $wgAuth;
-
-               $this->load();
-
-               if ( $this->mUsername == '' ) {
-                       return self::NO_NAME;
-               }
-
-               // We require a login token to prevent login CSRF
-               // Handle part of this before incrementing the throttle so
-               // token-less login attempts don't count towards the throttle
-               // but wrong-token attempts do.
-
-               // If the user doesn't have a login token yet, set one.
-               $token = self::getLoginToken();
-               if ( $token->wasNew() ) {
-                       return self::NEED_TOKEN;
-               }
-               // If the user didn't pass a login token, tell them we need one
-               if ( !$this->mToken ) {
-                       return self::NEED_TOKEN;
-               }
-
-               $throttleCount = self::incrementLoginThrottle( $this->mUsername );
-               if ( $throttleCount ) {
-                       $this->mThrottleWait = $throttleCount['wait'];
-                       return self::THROTTLED;
-               }
-
-               // Validate the login token
-               if ( !$token->match( $this->mToken ) ) {
-                       return self::WRONG_TOKEN;
-               }
-
-               // Load the current user now, and check to see if we're logging in as
-               // the same name. This is necessary because loading the current user
-               // (say by calling getName()) calls the UserLoadFromSession hook, which
-               // potentially creates the user in the database. Until we load $wgUser,
-               // checking for user existence using User::newFromName($name)->getId() below
-               // will effectively be using stale data.
-               if ( $this->getUser()->getName() === $this->mUsername ) {
-                       wfDebug( __METHOD__ . ": already logged in as {$this->mUsername}\n" );
-
-                       return self::SUCCESS;
-               }
-
-               $u = User::newFromName( $this->mUsername );
-               if ( $u === false ) {
-                       return self::ILLEGAL;
-               }
-
-               $msg = null;
-               // Give extensions a way to indicate the username has been updated,
-               // rather than telling the user the account doesn't exist.
-               if ( !Hooks::run( 'LoginUserMigrated', [ $u, &$msg ] ) ) {
-                       $this->mAbortLoginErrorMsg = $msg;
-                       return self::USER_MIGRATED;
-               }
-
-               if ( !User::isUsableName( $u->getName() ) ) {
-                       return self::ILLEGAL;
-               }
-
-               $isAutoCreated = false;
-               if ( $u->getId() == 0 ) {
-                       $status = $this->attemptAutoCreate( $u );
-                       if ( $status !== self::SUCCESS ) {
-                               return $status;
-                       } else {
-                               $isAutoCreated = true;
-                       }
-               } else {
-                       $u->load();
-               }
-
-               // Give general extensions, such as a captcha, a chance to abort logins
-               $abort = self::ABORTED;
-               if ( !Hooks::run( 'AbortLogin', [ $u, $this->mPassword, &$abort, &$msg ] ) ) {
-                       if ( !in_array( $abort, array_keys( self::$statusCodes ), true ) ) {
-                               throw new Exception( 'Invalid status code returned from AbortLogin hook: ' . $abort );
-                       }
-                       $this->mAbortLoginErrorMsg = $msg;
-                       return $abort;
-               }
-
-               global $wgBlockDisablesLogin;
-               if ( !$u->checkPassword( $this->mPassword ) ) {
-                       if ( $u->checkTemporaryPassword( $this->mPassword ) ) {
-                               /**
-                                * The e-mailed temporary password should not be used for actu-
-                                * al logins; that's a very sloppy habit, and insecure if an
-                                * attacker has a few seconds to click "search" on someone's
-                                * open mail reader.
-                                *
-                                * Allow it to be used only to reset the password a single time
-                                * to a new value, which won't be in the user's e-mail ar-
-                                * chives.
-                                *
-                                * For backwards compatibility, we'll still recognize it at the
-                                * login form to minimize surprises for people who have been
-                                * logging in with a temporary password for some time.
-                                *
-                                * As a side-effect, we can authenticate the user's e-mail ad-
-                                * dress if it's not already done, since the temporary password
-                                * was sent via e-mail.
-                                */
-                               if ( !$u->isEmailConfirmed() && !wfReadOnly() ) {
-                                       $u->confirmEmail();
-                                       $u->saveSettings();
-                               }
-
-                               // At this point we just return an appropriate code/ indicating
-                               // that the UI should show a password reset form; bot inter-
-                               // faces etc will probably just fail cleanly here.
-                               $this->mAbortLoginErrorMsg = 'resetpass-temp-emailed';
-                               $this->mTempPasswordUsed = true;
-                               $retval = self::RESET_PASS;
-                       } else {
-                               $retval = ( $this->mPassword == '' ) ? self::EMPTY_PASS : self::WRONG_PASS;
-                       }
-               } elseif ( $wgBlockDisablesLogin && $u->isBlocked() ) {
-                       // If we've enabled it, make it so that a blocked user cannot login
-                       $retval = self::USER_BLOCKED;
-               } elseif ( $this->checkUserPasswordExpired( $u ) == 'hard' ) {
-                       // Force reset now, without logging in
-                       $retval = self::RESET_PASS;
-                       $this->mAbortLoginErrorMsg = 'resetpass-expired';
-               } else {
-                       Hooks::run( 'UserLoggedIn', [ $u ] );
-                       $oldUser = $u;
-                       $wgAuth->updateUser( $u );
-                       if ( $oldUser !== $u ) {
-                               wfWarn( get_class( $wgAuth ) . '::updateUser() replaced the user object' );
-                       }
-                       $wgUser = $u;
-                       // This should set it for OutputPage and the Skin
-                       // which is needed or the personal links will be
-                       // wrong.
-                       $this->getContext()->setUser( $u );
-
-                       // Please reset throttle for successful logins, thanks!
-                       self::clearLoginThrottle( $this->mUsername );
-
-                       if ( $isAutoCreated ) {
-                               // Must be run after $wgUser is set, for correct new user log
-                               Hooks::run( 'AuthPluginAutoCreate', [ $u ] );
-                       }
-
-                       $retval = self::SUCCESS;
-               }
-               Hooks::run( 'LoginAuthenticateAudit', [ $u, $this->mPassword, $retval ] );
-
-               return $retval;
-       }
-
-       /**
-        * Increment the login attempt throttle hit count for the (username,current IP)
-        * tuple unless the throttle was already reached.
-        *
-        * @since 1.27 Return value changed.
-        * @param string $username The user name
-        * @return bool|array false if below limit or an array if above limit
-        *   Array contains keys wait, count, and throttleIndex
-        */
-       public static function incrementLoginThrottle( $username ) {
-               global $wgPasswordAttemptThrottle, $wgRequest;
-               $canUsername = User::getCanonicalName( $username, 'usable' );
-               $username = $canUsername !== false ? $canUsername : $username;
-
-               $throttleCount = 0;
-               if ( is_array( $wgPasswordAttemptThrottle ) ) {
-                       $throttleConfig = $wgPasswordAttemptThrottle;
-                       if ( isset( $wgPasswordAttemptThrottle['count'] ) ) {
-                               // old style. Convert for backwards compat.
-                               $throttleConfig = [ $wgPasswordAttemptThrottle ];
-                       }
-                       foreach ( $throttleConfig as $index => $specificThrottle ) {
-                               if ( isset( $specificThrottle['allIPs'] ) ) {
-                                       $ip = 'All';
-                               } else {
-                                       $ip = $wgRequest->getIP();
-                               }
-                               $throttleKey = wfGlobalCacheKey( 'password-throttle',
-                                       $index, $ip, md5( $username )
-                               );
-                               $count = $specificThrottle['count'];
-                               $period = $specificThrottle['seconds'];
-
-                               $cache = ObjectCache::getLocalClusterInstance();
-                               $throttleCount = $cache->get( $throttleKey );
-                               if ( !$throttleCount ) {
-                                       $cache->add( $throttleKey, 1, $period ); // start counter
-                               } elseif ( $throttleCount < $count ) {
-                                       $cache->incr( $throttleKey );
-                               } elseif ( $throttleCount >= $count ) {
-                                       $logMsg = 'Login attempt rejected because logins to '
-                                               . '{acct} from IP {ip} have been throttled for '
-                                               . '{period} seconds due to {count} failed attempts';
-                                       // If we are hitting a throttle for >= 50 attempts,
-                                       // it is much more likely to be an attack than someone
-                                       // simply forgetting their password, so log it at a
-                                       // higher level.
-                                       $level = $count >= 50 ? LogLevel::WARNING : LogLevel::INFO;
-                                       // It should be noted that once the throttle is hit,
-                                       // every attempt to login will generate the log message
-                                       // until the throttle expires, not just the attempt that
-                                       // puts the throttle over the top.
-                                       LoggerFactory::getInstance( 'password-throttle' )->log(
-                                               $level,
-                                               $logMsg,
-                                               [
-                                                       'ip' => $ip,
-                                                       'period' => $period,
-                                                       'acct' => $username,
-                                                       'count' => $count,
-                                                       'throttleIdentifier' => $index,
-                                                       'method' => __METHOD__
-                                               ]
-                                       );
-
-                                       return [
-                                               'throttleIndex' => $index,
-                                               'wait' => $period,
-                                               'count' => $count
-                                       ];
-                               }
-                       }
-               }
-               return false;
-       }
-
-       /**
-        * Increment the login attempt throttle hit count for the (username,current IP)
-        * tuple unless the throttle was already reached.
-        *
-        * @deprecated Use LoginForm::incrementLoginThrottle instead
-        * @param string $username The user name
-        * @return bool|int true if above throttle, or 0 (prior to 1.27, returned current count)
-        */
-       public static function incLoginThrottle( $username ) {
-               wfDeprecated( __METHOD__, "1.27" );
-               $res = self::incrementLoginThrottle( $username );
-               return is_array( $res ) ? true : 0;
-       }
-
-       /**
-        * Clear the login attempt throttle hit count for the (username,current IP) tuple.
-        * @param string $username The user name
-        * @return void
-        */
-       public static function clearLoginThrottle( $username ) {
-               global $wgRequest, $wgPasswordAttemptThrottle;
-               $canUsername = User::getCanonicalName( $username, 'usable' );
-               $username = $canUsername !== false ? $canUsername : $username;
-
-               if ( is_array( $wgPasswordAttemptThrottle ) ) {
-                       $throttleConfig = $wgPasswordAttemptThrottle;
-                       if ( isset( $wgPasswordAttemptThrottle['count'] ) ) {
-                               // old style. Convert for backwards compat.
-                               $throttleConfig = [ $wgPasswordAttemptThrottle ];
-                       }
-                       foreach ( $throttleConfig as $index => $specificThrottle ) {
-                               if ( isset( $specificThrottle['allIPs'] ) ) {
-                                       $ip = 'All';
-                               } else {
-                                       $ip = $wgRequest->getIP();
-                               }
-                               $throttleKey = wfGlobalCacheKey( 'password-throttle', $index,
-                                       $ip, md5( $username )
-                               );
-                               ObjectCache::getLocalClusterInstance()->delete( $throttleKey );
-                       }
-               }
-       }
-
-       /**
-        * Attempt to automatically create a user on login. Only succeeds if there
-        * is an external authentication method which allows it.
-        *
-        * @param User $user
-        *
-        * @return int Status code
-        */
-       function attemptAutoCreate( $user ) {
-               global $wgAuth;
-
-               if ( $this->getUser()->isBlockedFromCreateAccount() ) {
-                       wfDebug( __METHOD__ . ": user is blocked from account creation\n" );
-
-                       return self::CREATE_BLOCKED;
-               }
-
-               if ( !$wgAuth->autoCreate() ) {
-                       return self::NOT_EXISTS;
-               }
-
-               if ( !$wgAuth->userExists( $user->getName() ) ) {
-                       wfDebug( __METHOD__ . ": user does not exist\n" );
-
-                       return self::NOT_EXISTS;
-               }
-
-               if ( !$wgAuth->authenticate( $user->getName(), $this->mPassword ) ) {
-                       wfDebug( __METHOD__ . ": \$wgAuth->authenticate() returned false, aborting\n" );
-
-                       return self::WRONG_PLUGIN_PASS;
-               }
-
-               $abortError = '';
-               if ( !Hooks::run( 'AbortAutoAccount', [ $user, &$abortError ] ) ) {
-                       // Hook point to add extra creation throttles and blocks
-                       wfDebug( "LoginForm::attemptAutoCreate: a hook blocked creation: $abortError\n" );
-                       $this->mAbortLoginErrorMsg = $abortError;
-
-                       return self::ABORTED;
-               }
-
-               wfDebug( __METHOD__ . ": creating account\n" );
-               $status = $this->initUser( $user, true );
-
-               if ( !$status->isOK() ) {
-                       $errors = $status->getErrorsByType( 'error' );
-                       $this->mAbortLoginErrorMsg = $errors[0]['message'];
-
-                       return self::ABORTED;
-               }
-
-               return self::SUCCESS;
-       }
-
-       function processLogin() {
-               global $wgLang, $wgSecureLogin, $wgInvalidPasswordReset;
-
-               $authRes = $this->authenticateUserData();
-               switch ( $authRes ) {
-                       case self::SUCCESS:
-                               # We've verified now, update the real record
-                               $user = $this->getUser();
-                               $user->touch();
-
-                               if ( $user->requiresHTTPS() ) {
-                                       $this->mStickHTTPS = true;
-                               }
-
-                               if ( $wgSecureLogin && !$this->mStickHTTPS ) {
-                                       $user->setCookies( $this->mRequest, false, $this->mRemember );
-                               } else {
-                                       $user->setCookies( $this->mRequest, null, $this->mRemember );
-                               }
-                               self::clearLoginToken();
-
-                               // Reset the throttle
-                               self::clearLoginThrottle( $this->mUsername );
-
-                               $request = $this->getRequest();
-                               if ( $this->hasSessionCookie() || $this->mSkipCookieCheck ) {
-                                       /* Replace the language object to provide user interface in
-                                        * correct language immediately on this first page load.
-                                        */
-                                       $code = $request->getVal( 'uselang', $user->getOption( 'language' ) );
-                                       $userLang = Language::factory( $code );
-                                       $wgLang = $userLang;
-                                       RequestContext::getMain()->setLanguage( $userLang );
-                                       $this->getContext()->setLanguage( $userLang );
-                                       // Reset SessionID on Successful login (bug 40995)
-                                       $this->renewSessionId();
-                                       if ( $this->checkUserPasswordExpired( $this->getUser() ) == 'soft' ) {
-                                               $this->resetLoginForm( $this->msg( 'resetpass-expired-soft' ) );
-                                       } elseif ( $wgInvalidPasswordReset
-                                               && !$user->isValidPassword( $this->mPassword )
-                                       ) {
-                                               $status = $user->checkPasswordValidity(
-                                                       $this->mPassword,
-                                                       'login'
-                                               );
-                                               $this->resetLoginForm(
-                                                       $status->getMessage( 'resetpass-validity-soft' )
-                                               );
-                                       } else {
-                                               $this->successfulLogin();
-                                       }
-                               } else {
-                                       $this->cookieRedirectCheck( 'login' );
-                               }
-                               break;
-
-                       case self::NEED_TOKEN:
-                               $error = $this->mAbortLoginErrorMsg ?: 'nocookiesforlogin';
-                               $this->mainLoginForm( $this->msg( $error )->parse() );
-                               break;
-                       case self::WRONG_TOKEN:
-                               $error = $this->mAbortLoginErrorMsg ?: 'sessionfailure';
-                               $this->mainLoginForm( $this->msg( $error )->text() );
-                               break;
-                       case self::NO_NAME:
-                       case self::ILLEGAL:
-                               $error = $this->mAbortLoginErrorMsg ?: 'noname';
-                               $this->mainLoginForm( $this->msg( $error )->text() );
-                               break;
-                       case self::WRONG_PLUGIN_PASS:
-                               $error = $this->mAbortLoginErrorMsg ?: 'wrongpassword';
-                               $this->mainLoginForm( $this->msg( $error )->text() );
-                               break;
-                       case self::NOT_EXISTS:
-                               if ( $this->getUser()->isAllowed( 'createaccount' ) ) {
-                                       $error = $this->mAbortLoginErrorMsg ?: 'nosuchuser';
-                                       $this->mainLoginForm( $this->msg( $error,
-                                               wfEscapeWikiText( $this->mUsername ) )->parse() );
-                               } else {
-                                       $error = $this->mAbortLoginErrorMsg ?: 'nosuchusershort';
-                                       $this->mainLoginForm( $this->msg( $error,
-                                               wfEscapeWikiText( $this->mUsername ) )->text() );
-                               }
-                               break;
-                       case self::WRONG_PASS:
-                               $error = $this->mAbortLoginErrorMsg ?: 'wrongpassword';
-                               $this->mainLoginForm( $this->msg( $error )->text() );
-                               break;
-                       case self::EMPTY_PASS:
-                               $error = $this->mAbortLoginErrorMsg ?: 'wrongpasswordempty';
-                               $this->mainLoginForm( $this->msg( $error )->text() );
-                               break;
-                       case self::RESET_PASS:
-                               $error = $this->mAbortLoginErrorMsg ?: 'resetpass_announce';
-                               $this->resetLoginForm( $this->msg( $error ) );
-                               break;
-                       case self::CREATE_BLOCKED:
-                               $this->userBlockedMessage( $this->getUser()->isBlockedFromCreateAccount() );
-                               break;
-                       case self::THROTTLED:
-                               $error = $this->mAbortLoginErrorMsg ?: 'login-throttled';
-                               $this->mainLoginForm( $this->msg( $error )
-                                       ->durationParams( $this->mThrottleWait )->text()
-                               );
-                               break;
-                       case self::USER_BLOCKED:
-                               $error = $this->mAbortLoginErrorMsg ?: 'login-userblocked';
-                               $this->mainLoginForm( $this->msg( $error, $this->mUsername )->escaped() );
-                               break;
-                       case self::ABORTED:
-                               $error = $this->mAbortLoginErrorMsg ?: 'login-abort-generic';
-                               $this->mainLoginForm( $this->msg( $error,
-                                               wfEscapeWikiText( $this->mUsername ) )->text() );
-                               break;
-                       case self::USER_MIGRATED:
-                               $error = $this->mAbortLoginErrorMsg ?: 'login-migrated-generic';
-                               $params = [];
-                               if ( is_array( $error ) ) {
-                                       $error = array_shift( $this->mAbortLoginErrorMsg );
-                                       $params = $this->mAbortLoginErrorMsg;
-                               }
-                               $this->mainLoginForm( $this->msg( $error, $params )->text() );
-                               break;
-                       default:
-                               throw new MWException( 'Unhandled case value' );
-               }
-
-               LoggerFactory::getInstance( 'authmanager' )->info( 'Login attempt', [
-                       'event' => 'login',
-                       'successful' => $authRes === self::SUCCESS,
-                       'status' => LoginForm::$statusCodes[$authRes],
-               ] );
-       }
-
-       /**
-        * Show the Special:ChangePassword form, with custom message
-        * @param Message $msg
-        */
-       protected function resetLoginForm( Message $msg ) {
-               // Allow hooks to explain this password reset in more detail
-               Hooks::run( 'LoginPasswordResetMessage', [ &$msg, $this->mUsername ] );
-               $reset = new SpecialChangePasswordPreAuthManager();
-               $derivative = new DerivativeContext( $this->getContext() );
-               $derivative->setTitle( $reset->getPageTitle() );
-               $reset->setContext( $derivative );
-               if ( !$this->mTempPasswordUsed ) {
-                       $reset->setOldPasswordMessage( 'oldpassword' );
-               }
-               $reset->setChangeMessage( $msg );
-               $reset->execute( null );
-       }
-
-       /**
-        * @param User $u
-        * @param bool $throttle
-        * @param string $emailTitle Message name of email title
-        * @param string $emailText Message name of email text
-        * @return Status
-        */
-       function mailPasswordInternal( $u, $throttle = true, $emailTitle = 'passwordremindertitle',
-               $emailText = 'passwordremindertext'
-       ) {
-               global $wgNewPasswordExpiry, $wgMinimalPasswordLength;
-
-               if ( $u->getEmail() == '' ) {
-                       return Status::newFatal( 'noemail', $u->getName() );
-               }
-               $ip = $this->getRequest()->getIP();
-               if ( !$ip ) {
-                       return Status::newFatal( 'badipaddress' );
-               }
-
-               $currentUser = $this->getUser();
-               Hooks::run( 'User::mailPasswordInternal', [ &$currentUser, &$ip, &$u ] );
-
-               $np = PasswordFactory::generateRandomPasswordString( $wgMinimalPasswordLength );
-               $u->setNewpassword( $np, $throttle );
-               $u->saveSettings();
-               $userLanguage = $u->getOption( 'language' );
-
-               $mainPage = Title::newMainPage();
-               $mainPageUrl = $mainPage->getCanonicalURL();
-
-               $m = $this->msg( $emailText, $ip, $u->getName(), $np, '<' . $mainPageUrl . '>',
-                       round( $wgNewPasswordExpiry / 86400 ) )->inLanguage( $userLanguage )->text();
-               $result = $u->sendMail( $this->msg( $emailTitle )->inLanguage( $userLanguage )->text(), $m );
-
-               return $result;
-       }
-
-       /**
-        * Run any hooks registered for logins, then HTTP redirect to
-        * $this->mReturnTo (or Main Page if that's undefined).  Formerly we had a
-        * nice message here, but that's really not as useful as just being sent to
-        * wherever you logged in from.  It should be clear that the action was
-        * successful, given the lack of error messages plus the appearance of your
-        * name in the upper right.
-        *
-        * @private
-        */
-       function successfulLogin() {
-               # Run any hooks; display injected HTML if any, else redirect
-               $currentUser = $this->getUser();
-               $injected_html = '';
-               $direct = RequestContext::getMain()->getRequest()->wasPosted();
-               Hooks::run( 'UserLoginComplete', [ &$currentUser, &$injected_html, $direct ] );
-
-               if ( $injected_html !== '' ) {
-                       $this->displaySuccessfulAction( 'success', $this->msg( 'loginsuccesstitle' ),
-                               'loginsuccess', $injected_html );
-               } else {
-                       $this->executeReturnTo( 'successredirect' );
-               }
-       }
-
-       /**
-        * Run any hooks registered for logins, then display a message welcoming
-        * the user.
-        *
-        * @private
-        */
-       function successfulCreation() {
-               # Run any hooks; display injected HTML
-               $currentUser = $this->getUser();
-               $injected_html = '';
-               $welcome_creation_msg = 'welcomecreation-msg';
-               $direct = RequestContext::getMain()->getRequest()->wasPosted();
-
-               Hooks::run( 'UserLoginComplete', [ &$currentUser, &$injected_html, $direct ] );
-
-               /**
-                * Let any extensions change what message is shown.
-                * @see https://www.mediawiki.org/wiki/Manual:Hooks/BeforeWelcomeCreation
-                * @since 1.18
-                */
-               Hooks::run( 'BeforeWelcomeCreation', [ &$welcome_creation_msg, &$injected_html ] );
-
-               $this->displaySuccessfulAction(
-                       'signup',
-                       $this->msg( 'welcomeuser', $this->getUser()->getName() ),
-                       $welcome_creation_msg, $injected_html
-               );
-       }
-
-       /**
-        * Display a "successful action" page.
-        *
-        * @param string $type Condition of return to; see `executeReturnTo`
-        * @param string|Message $title Page's title
-        * @param string $msgname
-        * @param string $injected_html
-        */
-       private function displaySuccessfulAction( $type, $title, $msgname, $injected_html ) {
-               $out = $this->getOutput();
-               $out->setPageTitle( $title );
-               if ( $msgname ) {
-                       $out->addWikiMsg( $msgname, wfEscapeWikiText( $this->getUser()->getName() ) );
-               }
-
-               $out->addHTML( $injected_html );
-
-               $this->executeReturnTo( $type );
-       }
-
-       /**
-        * Output a message that informs the user that they cannot create an account because
-        * there is a block on them or their IP which prevents account creation.  Note that
-        * User::isBlockedFromCreateAccount(), which gets this block, ignores the 'hardblock'
-        * setting on blocks (bug 13611).
-        * @param Block $block The block causing this error
-        * @throws ErrorPageError
-        */
-       function userBlockedMessage( Block $block ) {
-               # Let's be nice about this, it's likely that this feature will be used
-               # for blocking large numbers of innocent people, e.g. range blocks on
-               # schools. Don't blame it on the user. There's a small chance that it
-               # really is the user's fault, i.e. the username is blocked and they
-               # haven't bothered to log out before trying to create an account to
-               # evade it, but we'll leave that to their guilty conscience to figure
-               # out.
-               $errorParams = [
-                       $block->getTarget(),
-                       $block->mReason ? $block->mReason : $this->msg( 'blockednoreason' )->text(),
-                       $block->getByName()
-               ];
-
-               if ( $block->getType() === Block::TYPE_RANGE ) {
-                       $errorMessage = 'cantcreateaccount-range-text';
-                       $errorParams[] = $this->getRequest()->getIP();
-               } else {
-                       $errorMessage = 'cantcreateaccount-text';
-               }
-
-               throw new ErrorPageError(
-                       'cantcreateaccounttitle',
-                       $errorMessage,
-                       $errorParams
-               );
-       }
-
-       /**
-        * Add a "return to" link or redirect to it.
-        * Extensions can use this to reuse the "return to" logic after
-        * inject steps (such as redirection) into the login process.
-        *
-        * @param string $type One of the following:
-        *    - error: display a return to link ignoring $wgRedirectOnLogin
-        *    - signup: display a return to link using $wgRedirectOnLogin if needed
-        *    - success: display a return to link using $wgRedirectOnLogin if needed
-        *    - successredirect: send an HTTP redirect using $wgRedirectOnLogin if needed
-        * @param string $returnTo
-        * @param array|string $returnToQuery
-        * @param bool $stickHTTPs Keep redirect link on HTTPs
-        * @since 1.22
-        */
-       public function showReturnToPage(
-               $type, $returnTo = '', $returnToQuery = '', $stickHTTPs = false
-       ) {
-               $this->mReturnTo = $returnTo;
-               $this->mReturnToQuery = $returnToQuery;
-               $this->mStickHTTPS = $stickHTTPs;
-               $this->executeReturnTo( $type );
-       }
-
-       /**
-        * Add a "return to" link or redirect to it.
-        *
-        * @param string $type One of the following:
-        *    - error: display a return to link ignoring $wgRedirectOnLogin
-        *    - signup: display a return to link using $wgRedirectOnLogin if needed
-        *    - success: display a return to link using $wgRedirectOnLogin if needed
-        *    - successredirect: send an HTTP redirect using $wgRedirectOnLogin if needed
-        */
-       private function executeReturnTo( $type ) {
-               global $wgRedirectOnLogin, $wgSecureLogin;
-
-               if ( $type != 'error' && $wgRedirectOnLogin !== null ) {
-                       $returnTo = $wgRedirectOnLogin;
-                       $returnToQuery = [];
-               } else {
-                       $returnTo = $this->mReturnTo;
-                       $returnToQuery = wfCgiToArray( $this->mReturnToQuery );
-               }
-
-               // Allow modification of redirect behavior
-               Hooks::run( 'PostLoginRedirect', [ &$returnTo, &$returnToQuery, &$type ] );
-
-               $returnToTitle = Title::newFromText( $returnTo );
-               if ( !$returnToTitle ) {
-                       $returnToTitle = Title::newMainPage();
-               }
-
-               if ( $wgSecureLogin && !$this->mStickHTTPS ) {
-                       $options = [ 'http' ];
-                       $proto = PROTO_HTTP;
-               } elseif ( $wgSecureLogin ) {
-                       $options = [ 'https' ];
-                       $proto = PROTO_HTTPS;
-               } else {
-                       $options = [];
-                       $proto = PROTO_RELATIVE;
-               }
-
-               if ( $type == 'successredirect' ) {
-                       $redirectUrl = $returnToTitle->getFullURL( $returnToQuery, false, $proto );
-                       $this->getOutput()->redirect( $redirectUrl );
-               } else {
-                       $this->getOutput()->addReturnTo( $returnToTitle, $returnToQuery, null, $options );
-               }
-       }
-
-       /**
-        * @param string $msg
-        * @param string $msgtype
-        * @throws ErrorPageError
-        * @throws Exception
-        * @throws FatalError
-        * @throws MWException
-        * @throws PermissionsError
-        * @throws ReadOnlyError
-        * @private
-        */
-       function mainLoginForm( $msg, $msgtype = 'error' ) {
-               global $wgEnableEmail, $wgEnableUserEmail;
-               global $wgHiddenPrefs, $wgLoginLanguageSelector;
-               global $wgAuth, $wgEmailConfirmToEdit;
-               global $wgSecureLogin, $wgPasswordResetRoutes;
-               global $wgExtendedLoginCookieExpiration, $wgCookieExpiration;
-
-               $titleObj = $this->getPageTitle();
-               $user = $this->getUser();
-               $out = $this->getOutput();
-
-               if ( $this->mType == 'signup' ) {
-                       // Block signup here if in readonly. Keeps user from
-                       // going through the process (filling out data, etc)
-                       // and being informed later.
-                       $permErrors = $titleObj->getUserPermissionsErrors( 'createaccount', $user, true );
-                       if ( count( $permErrors ) ) {
-                               throw new PermissionsError( 'createaccount', $permErrors );
-                       } elseif ( $user->isBlockedFromCreateAccount() ) {
-                               $this->userBlockedMessage( $user->isBlockedFromCreateAccount() );
-
-                               return;
-                       } elseif ( wfReadOnly() ) {
-                               throw new ReadOnlyError;
-                       }
-               }
-
-               // Pre-fill username (if not creating an account, bug 44775).
-               if ( $this->mUsername == '' && $this->mType != 'signup' ) {
-                       if ( $user->isLoggedIn() ) {
-                               $this->mUsername = $user->getName();
-                       } else {
-                               $this->mUsername = $this->getRequest()->getSession()->suggestLoginUsername();
-                       }
-               }
-
-               // Generic styles and scripts for both login and signup form
-               $out->addModuleStyles( [
-                       'mediawiki.ui',
-                       'mediawiki.ui.button',
-                       'mediawiki.ui.checkbox',
-                       'mediawiki.ui.input',
-                       'mediawiki.special.userlogin.common.styles'
-               ] );
-
-               if ( $this->mType == 'signup' ) {
-                       // Additional styles and scripts for signup form
-                       $out->addModules( [
-                               'mediawiki.special.userlogin.signup.js'
-                       ] );
-                       $out->addModuleStyles( [
-                               'mediawiki.special.userlogin.signup.styles'
-                       ] );
-
-                       $template = new UsercreateTemplate( $this->getConfig() );
-
-                       // Must match number of benefits defined in messages
-                       $template->set( 'benefitCount', 3 );
-
-                       $q = 'action=submitlogin&type=signup';
-                       $linkq = 'type=login';
-               } else {
-                       // Additional styles for login form
-                       $out->addModuleStyles( [
-                               'mediawiki.special.userlogin.login.styles'
-                       ] );
-
-                       $template = new UserloginTemplate( $this->getConfig() );
-
-                       $q = 'action=submitlogin&type=login';
-                       $linkq = 'type=signup';
-               }
-
-               if ( $this->mReturnTo !== '' ) {
-                       $returnto = '&returnto=' . wfUrlencode( $this->mReturnTo );
-                       if ( $this->mReturnToQuery !== '' ) {
-                               $returnto .= '&returntoquery=' .
-                                       wfUrlencode( $this->mReturnToQuery );
-                       }
-                       $q .= $returnto;
-                       $linkq .= $returnto;
-               }
-
-               # Don't show a "create account" link if the user can't.
-               if ( $this->showCreateOrLoginLink( $user ) ) {
-                       # Pass any language selection on to the mode switch link
-                       if ( $wgLoginLanguageSelector && $this->mLanguage ) {
-                               $linkq .= '&uselang=' . $this->mLanguage;
-                       }
-                       // Supply URL, login template creates the button.
-                       $template->set( 'createOrLoginHref', $titleObj->getLocalURL( $linkq ) );
-               } else {
-                       $template->set( 'link', '' );
-               }
-
-               $resetLink = $this->mType == 'signup'
-                       ? null
-                       : is_array( $wgPasswordResetRoutes ) && in_array( true, array_values( $wgPasswordResetRoutes ) );
-
-               $template->set( 'header', '' );
-               $template->set( 'formheader', '' );
-               $template->set( 'skin', $this->getSkin() );
-               $template->set( 'name', $this->mUsername );
-               $template->set( 'password', $this->mPassword );
-               $template->set( 'retype', $this->mRetype );
-               $template->set( 'createemailset', $this->mCreateaccountMail );
-               $template->set( 'email', $this->mEmail );
-               $template->set( 'realname', $this->mRealName );
-               $template->set( 'domain', $this->mDomain );
-               $template->set( 'reason', $this->mReason );
-
-               $template->set( 'action', $titleObj->getLocalURL( $q ) );
-               $template->set( 'message', $msg );
-               $template->set( 'messagetype', $msgtype );
-               $template->set( 'createemail', $wgEnableEmail && $user->isLoggedIn() );
-               $template->set( 'userealname', !in_array( 'realname', $wgHiddenPrefs ) );
-               $template->set( 'useemail', $wgEnableEmail );
-               $template->set( 'emailrequired', $wgEmailConfirmToEdit );
-               $template->set( 'emailothers', $wgEnableUserEmail );
-               $template->set( 'canreset', $wgAuth->allowPasswordChange() );
-               $template->set( 'resetlink', $resetLink );
-               $template->set( 'canremember', $wgExtendedLoginCookieExpiration === null ?
-                       ( $wgCookieExpiration > 0 ) :
-                       ( $wgExtendedLoginCookieExpiration > 0 ) );
-               $template->set( 'usereason', $user->isLoggedIn() );
-               $template->set( 'remember', $this->mRemember );
-               $template->set( 'cansecurelogin', ( $wgSecureLogin === true ) );
-               $template->set( 'stickhttps', (int)$this->mStickHTTPS );
-               $template->set( 'loggedin', $user->isLoggedIn() );
-               $template->set( 'loggedinuser', $user->getName() );
-
-               if ( $this->mType == 'signup' ) {
-                       $template->set( 'token', self::getCreateaccountToken()->toString() );
-               } else {
-                       $template->set( 'token', self::getLoginToken()->toString() );
-               }
-
-               # Prepare language selection links as needed
-               if ( $wgLoginLanguageSelector ) {
-                       $template->set( 'languages', $this->makeLanguageSelector() );
-                       if ( $this->mLanguage ) {
-                               $template->set( 'uselang', $this->mLanguage );
-                       }
-               }
-
-               $template->set( 'secureLoginUrl', $this->mSecureLoginUrl );
-               // Use signupend-https for HTTPS requests if it's not blank, signupend otherwise
-               $usingHTTPS = $this->mRequest->getProtocol() == 'https';
-               $signupendHTTPS = $this->msg( 'signupend-https' );
-               if ( $usingHTTPS && !$signupendHTTPS->isBlank() ) {
-                       $template->set( 'signupend', $signupendHTTPS->parse() );
-               } else {
-                       $template->set( 'signupend', $this->msg( 'signupend' )->parse() );
-               }
-
-               // If using HTTPS coming from HTTP, then the 'fromhttp' parameter must be preserved
-               if ( $usingHTTPS ) {
-                       $template->set( 'fromhttp', $this->mFromHTTP );
-               }
-
-               // Give authentication and captcha plugins a chance to modify the form
-               $wgAuth->modifyUITemplate( $template, $this->mType );
-               if ( $this->mType == 'signup' ) {
-                       Hooks::run( 'UserCreateForm', [ &$template ] );
-               } else {
-                       Hooks::run( 'UserLoginForm', [ &$template ] );
-               }
-
-               $out->disallowUserJs(); // just in case...
-               $out->addTemplate( $template );
-       }
-
-       /**
-        * Whether the login/create account form should display a link to the
-        * other form (in addition to whatever the skin provides).
-        *
-        * @param User $user
-        * @return bool
-        */
-       private function showCreateOrLoginLink( &$user ) {
-               if ( $this->mType == 'signup' ) {
-                       return true;
-               } elseif ( $user->isAllowed( 'createaccount' ) ) {
-                       return true;
-               } else {
-                       return false;
-               }
-       }
-
-       /**
-        * Check if a session cookie is present.
-        *
-        * This will not pick up a cookie set during _this_ request, but is meant
-        * to ensure that the client is returning the cookie which was set on a
-        * previous pass through the system.
-        *
-        * @private
-        * @return bool
-        */
-       function hasSessionCookie() {
-               global $wgDisableCookieCheck, $wgInitialSessionId;
-
-               return $wgDisableCookieCheck || (
-                       $wgInitialSessionId &&
-                       $this->getRequest()->getSession()->getId() === (string)$wgInitialSessionId
-               );
-       }
-
-       /**
-        * Get the login token from the current session
-        * @since 1.27 returns a MediaWiki\Session\Token instead of a string
-        * @return MediaWiki\Session\Token
-        */
-       public static function getLoginToken() {
-               global $wgRequest;
-               return $wgRequest->getSession()->getToken( '', 'login' );
-       }
-
-       /**
-        * Formerly randomly generated a login token that would be returned by
-        * $this->getLoginToken().
-        *
-        * Since 1.27, this is a no-op. The token is generated as necessary by
-        * $this->getLoginToken().
-        *
-        * @deprecated since 1.27
-        */
-       public static function setLoginToken() {
-               wfDeprecated( __METHOD__, '1.27' );
-       }
-
-       /**
-        * Remove any login token attached to the current session
-        */
-       public static function clearLoginToken() {
-               global $wgRequest;
-               $wgRequest->getSession()->resetToken( 'login' );
-       }
-
-       /**
-        * Get the createaccount token from the current session
-        * @since 1.27 returns a MediaWiki\Session\Token instead of a string
-        * @return MediaWiki\Session\Token
-        */
-       public static function getCreateaccountToken() {
-               global $wgRequest;
-               return $wgRequest->getSession()->getToken( '', 'createaccount' );
-       }
-
-       /**
-        * Formerly randomly generated a createaccount token that would be returned
-        * by $this->getCreateaccountToken().
-        *
-        * Since 1.27, this is a no-op. The token is generated as necessary by
-        * $this->getCreateaccountToken().
-        *
-        * @deprecated since 1.27
-        */
-       public static function setCreateaccountToken() {
-               wfDeprecated( __METHOD__, '1.27' );
-       }
-
-       /**
-        * Remove any createaccount token attached to the current session
-        */
-       public static function clearCreateaccountToken() {
-               global $wgRequest;
-               $wgRequest->getSession()->resetToken( 'createaccount' );
-       }
-
-       /**
-        * Renew the user's session id, using strong entropy
-        */
-       private function renewSessionId() {
-               global $wgSecureLogin, $wgCookieSecure;
-               if ( $wgSecureLogin && !$this->mStickHTTPS ) {
-                       $wgCookieSecure = false;
-               }
-
-               SessionManager::getGlobalSession()->resetId();
-               SessionManager::getGlobalSession()->resetAllTokens();
-       }
-
-       /**
-        * @param string $type
-        * @private
-        */
-       function cookieRedirectCheck( $type ) {
-               $titleObj = SpecialPage::getTitleFor( 'Userlogin' );
-               $query = [ 'wpCookieCheck' => $type ];
-               if ( $this->mReturnTo !== '' ) {
-                       $query['returnto'] = $this->mReturnTo;
-                       $query['returntoquery'] = $this->mReturnToQuery;
-               }
-               $check = $titleObj->getFullURL( $query );
-
-               $this->getOutput()->redirect( $check );
-       }
-
-       /**
-        * @param string $type
-        * @private
-        */
-       function onCookieRedirectCheck( $type ) {
-               if ( !$this->hasSessionCookie() ) {
-                       if ( $type == 'new' ) {
-                               $this->mainLoginForm( $this->msg( 'nocookiesnew' )->parse() );
-                       } elseif ( $type == 'login' ) {
-                               $this->mainLoginForm( $this->msg( 'nocookieslogin' )->parse() );
-                       } else {
-                               # shouldn't happen
-                               $this->mainLoginForm( $this->msg( 'error' )->text() );
-                       }
-               } else {
-                       $this->successfulLogin();
-               }
-       }
-
-       /**
-        * Produce a bar of links which allow the user to select another language
-        * during login/registration but retain "returnto"
-        *
-        * @return string
-        */
-       function makeLanguageSelector() {
-               $msg = $this->msg( 'loginlanguagelinks' )->inContentLanguage();
-               if ( $msg->isBlank() ) {
-                       return '';
-               }
-               $langs = explode( "\n", $msg->text() );
-               $links = [];
-               foreach ( $langs as $lang ) {
-                       $lang = trim( $lang, '* ' );
-                       $parts = explode( '|', $lang );
-                       if ( count( $parts ) >= 2 ) {
-                               $links[] = $this->makeLanguageSelectorLink( $parts[0], trim( $parts[1] ) );
-                       }
-               }
-
-               return count( $links ) > 0 ? $this->msg( 'loginlanguagelabel' )->rawParams(
-                       $this->getLanguage()->pipeList( $links ) )->escaped() : '';
-       }
-
-       /**
-        * Create a language selector link for a particular language
-        * Links back to this page preserving type and returnto
-        *
-        * @param string $text Link text
-        * @param string $lang Language code
-        * @return string
-        */
-       function makeLanguageSelectorLink( $text, $lang ) {
-               if ( $this->getLanguage()->getCode() == $lang ) {
-                       // no link for currently used language
-                       return htmlspecialchars( $text );
-               }
-               $query = [ 'uselang' => $lang ];
-               if ( $this->mType == 'signup' ) {
-                       $query['type'] = 'signup';
-               }
-               if ( $this->mReturnTo !== '' ) {
-                       $query['returnto'] = $this->mReturnTo;
-                       $query['returntoquery'] = $this->mReturnToQuery;
-               }
-
-               $attr = [];
-               $targetLanguage = Language::factory( $lang );
-               $attr['lang'] = $attr['hreflang'] = $targetLanguage->getHtmlCode();
-
-               return Linker::linkKnown(
-                       $this->getPageTitle(),
-                       htmlspecialchars( $text ),
-                       $attr,
-                       $query
-               );
-       }
-
-       protected function getGroupName() {
-               return 'login';
-       }
-
-       /**
-        * Private function to check password expiration, until AuthManager comes
-        * along to handle that.
-        * @param User $user
-        * @return string|bool
-        */
-       private function checkUserPasswordExpired( User $user ) {
-               global $wgPasswordExpireGrace;
-               $dbr = wfGetDB( DB_SLAVE );
-               $ts = $dbr->selectField( 'user', 'user_password_expires', [ 'user_id' => $user->getId() ] );
-
-               $expired = false;
-               $now = wfTimestamp();
-               $expUnix = wfTimestamp( TS_UNIX, $ts );
-               if ( $ts !== null && $expUnix < $now ) {
-                       $expired = ( $expUnix + $wgPasswordExpireGrace < $now ) ? 'hard' : 'soft';
-               }
-               return $expired;
-       }
-
-       protected function getSubpagesForPrefixSearch() {
-               return [ 'signup' ];
-       }
-}
diff --git a/includes/specials/pre-authmanager/SpecialUserlogout.php b/includes/specials/pre-authmanager/SpecialUserlogout.php
deleted file mode 100644 (file)
index 6d6a714..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-<?php
-/**
- * Implements Special:Userlogout
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- * @ingroup SpecialPage
- */
-
-/**
- * Implements Special:Userlogout
- *
- * @ingroup SpecialPage
- */
-class SpecialUserlogoutPreAuthManager extends UnlistedSpecialPage {
-       function __construct() {
-               parent::__construct( 'Userlogout' );
-       }
-
-       public function doesWrites() {
-               return true;
-       }
-
-       function execute( $par ) {
-               /**
-                * Some satellite ISPs use broken precaching schemes that log people out straight after
-                * they're logged in (bug 17790). Luckily, there's a way to detect such requests.
-                */
-               if ( isset( $_SERVER['REQUEST_URI'] ) && strpos( $_SERVER['REQUEST_URI'], '&amp;' ) !== false ) {
-                       wfDebug( "Special:Userlogout request {$_SERVER['REQUEST_URI']} looks suspicious, denying.\n" );
-                       throw new HttpError( 400, $this->msg( 'suspicious-userlogout' ), $this->msg( 'loginerror' ) );
-               }
-
-               $this->setHeaders();
-               $this->outputHeader();
-
-               // Make sure it's possible to log out
-               $session = MediaWiki\Session\SessionManager::getGlobalSession();
-               if ( !$session->canSetUser() ) {
-                       throw new ErrorPageError(
-                               'cannotlogoutnow-title',
-                               'cannotlogoutnow-text',
-                               [
-                                       $session->getProvider()->describe( RequestContext::getMain()->getLanguage() )
-                               ]
-                       );
-               }
-
-               $user = $this->getUser();
-               $oldName = $user->getName();
-               $user->logout();
-
-               $loginURL = SpecialPage::getTitleFor( 'Userlogin' )->getFullURL(
-                       $this->getRequest()->getValues( 'returnto', 'returntoquery' ) );
-
-               $out = $this->getOutput();
-               $out->addWikiMsg( 'logouttext', $loginURL );
-
-               // Hook.
-               $injected_html = '';
-               Hooks::run( 'UserLogoutComplete', [ &$user, &$injected_html, $oldName ] );
-               $out->addHTML( $injected_html );
-
-               $out->returnToMain();
-       }
-
-       protected function getGroupName() {
-               return 'login';
-       }
-}
diff --git a/includes/templates/Usercreate.php b/includes/templates/Usercreate.php
deleted file mode 100644 (file)
index 0a5aa61..0000000
+++ /dev/null
@@ -1,308 +0,0 @@
-<?php
-// @codingStandardsIgnoreFile
-/**
- * Html form for account creation (since 1.22 with VForm appearance).
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- * @ingroup Templates
- * @deprecated Will be removed when AuthManager lands.
- *   The signup form will be generated via HTMLForm.
- */
-
-class UsercreateTemplate extends BaseTemplate {
-       /**
-        * Extensions (AntiSpoof and TitleBlacklist) call this in response to
-        * UserCreateForm hook to add checkboxes to the create account form.
-        */
-       function addInputItem( $name, $value, $type, $msg, $helptext = false ) {
-               $this->data['extraInput'][] = [
-                       'name' => $name,
-                       'value' => $value,
-                       'type' => $type,
-                       'msg' => $msg,
-                       'helptext' => $helptext,
-               ];
-       }
-
-       function execute() {
-?>
-<div class="mw-ui-container">
-       <?php if ( $this->haveData( 'languages' ) ) { ?>
-               <div id="languagelinks">
-                       <p><?php $this->html( 'languages' ); ?></p>
-               </div>
-       <?php }
-             if ( !wfMessage( 'signupstart' )->isDisabled() ) { ?>
-               <div id="signupstart"><?php $this->msgWiki( 'signupstart' ); ?></div>
-       <?php } ?>
-       <div id="userloginForm">
-               <form name="userlogin2" id="userlogin2" class="mw-ui-vform" method="post" action="<?php $this->text( 'action' ); ?>">
-                       <section class="mw-form-header">
-                               <?php $this->html( 'header' ); ?>
-                       </section>
-                       <!-- This element is used by the mediawiki.special.userlogin.signup.js module. -->
-                       <div
-                               id="mw-createacct-status-area"
-                               <?php if ( $this->data['message'] ) { ?>
-                                       class="<?php echo $this->data['messagetype']; ?>box"
-                               <?php } else { ?>
-                                       style="display: none;"
-                               <?php } ?>
-                       >
-                       <?php if ( $this->data['message'] ) { ?>
-                                       <?php if ( $this->data['messagetype'] == 'error' ) { ?>
-                                               <strong><?php $this->msg( 'createacct-error' ); ?></strong>
-                                               <br />
-                                       <?php } ?>
-                                       <?php $this->html( 'message' ); ?>
-                       <?php } ?>
-                       </div>
-
-                       <?php if ( $this->data['formheader'] ) { ?>
-                               <div class="mw-form-formheader">
-                                       <?php $this->html( 'formheader' ); /* extensions such as MobileFrontend add html here */ ?>
-                               </div>
-                       <?php } ?>
-
-                       <div class="mw-ui-vform-field">
-                               <label for='wpName2'>
-                                       <?php $this->msg( 'userlogin-yourname' ); ?>
-
-                                       <span class="mw-ui-flush-right"><?php echo $this->getMsg( 'createacct-helpusername' )->parse(); ?></span>
-                               </label>
-                               <?php
-                               echo Html::input( 'wpName', $this->data['name'], 'text', [
-                                       'class' => 'mw-ui-input loginText',
-                                       'id' => 'wpName2',
-                                       'tabindex' => '1',
-                                       'size' => '20',
-                                       'required',
-                                       'placeholder' => $this->getMsg( $this->data['loggedin'] ?
-                                               'createacct-another-username-ph' : 'userlogin-yourname-ph' )->text(),
-                               ] );
-                               ?>
-                       </div>
-
-                       <div class="mw-ui-vform-field">
-                               <?php if ( $this->data['createemail'] ) { ?>
-                                       <div class="mw-ui-checkbox">
-                                               <input name="wpCreateaccountMail" type="checkbox" value="1" id="wpCreateaccountMail" tabindex="2"
-                                                       <?php if ( $this->data['createemailset'] ) {
-                                                               echo 'checked="checked"';
-                                                       } ?>
-                                               ><label for="wpCreateaccountMail">
-                                                       <?php $this->msg( 'createaccountmail' ); ?>
-                                               </label>
-                                       </div>
-                               <?php } ?>
-                       </div>
-
-                       <div class="mw-ui-vform-field mw-row-password">
-                               <label for='wpPassword2'><?php $this->msg( 'userlogin-yourpassword' ); ?></label>
-                               <?php
-                               echo Html::input( 'wpPassword', null, 'password', [
-                                       'class' => 'mw-ui-input loginPassword',
-                                       'id' => 'wpPassword2',
-                                       'tabindex' => '3',
-                                       'size' => '20',
-                                       'required',
-                                       'placeholder' => $this->getMsg( 'createacct-yourpassword-ph' )->text()
-                               ] + User::passwordChangeInputAttribs() );
-                               ?>
-                       </div>
-
-                       <?php
-                       if ( $this->data['usedomain'] ) {
-                               $select = new XmlSelect( 'wpDomain', false, $this->data['domain'] );
-                               $select->setAttribute( 'tabindex', 4 );
-                               foreach ( $this->data['domainnames'] as $dom ) {
-                                       $select->addOption( $dom );
-                               }
-                       ?>
-                               <div class="mw-ui-vform-field" id="mw-user-domain-section">
-                                       <label for="wpDomain"><?php $this->msg( 'yourdomainname' ); ?></label>
-                                       <div>
-                                               <?php echo $select->getHTML(); ?>
-                                       </div>
-                               </div>
-                       <?php } ?>
-
-                       <div class="mw-ui-vform-field mw-row-password">
-                               <label for='wpRetype'><?php $this->msg( 'createacct-yourpasswordagain' ); ?></label>
-                               <?php
-                               echo Html::input( 'wpRetype', null, 'password', [
-                                       'class' => 'mw-ui-input loginPassword',
-                                       'id' => 'wpRetype',
-                                       'tabindex' => '5',
-                                       'size' => '20',
-                                       'required',
-                                       'placeholder' => $this->getMsg( 'createacct-yourpasswordagain-ph' )->text()
-                               ] + User::passwordChangeInputAttribs() );
-                               ?>
-                       </div>
-
-                       <div class="mw-ui-vform-field">
-                               <?php if ( $this->data['useemail'] ) { ?>
-                                       <label for='wpEmail'>
-                                               <?php
-                                                       $this->msg( $this->data['emailrequired'] ?
-                                                               'createacct-emailrequired' :
-                                                               'createacct-emailoptional'
-                                                       );
-                                               ?>
-                                       </label>
-                                       <?php
-                                               echo Html::input( 'wpEmail', $this->data['email'], 'email', [
-                                                       'class' => 'mw-ui-input loginText',
-                                                       'id' => 'wpEmail',
-                                                       'tabindex' => '6',
-                                                       'size' => '20',
-                                                       'required' => $this->data['emailrequired'],
-                                                       'placeholder' => $this->getMsg( $this->data['loggedin'] ?
-                                                               'createacct-another-email-ph' : 'createacct-email-ph' )->text()
-                                               ] );
-                                       ?>
-                               <?php } ?>
-                       </div>
-
-                       <?php if ( $this->data['userealname'] ) { ?>
-                               <div class="mw-ui-vform-field">
-                                       <label for='wpRealName'><?php $this->msg( 'createacct-realname' ); ?></label>
-                                       <input type='text' class='mw-ui-input loginText' name="wpRealName" id="wpRealName"
-                                               tabindex="7"
-                                               value="<?php $this->text( 'realname' ); ?>" size='20' />
-                                       <div class="prefsectiontip">
-                                               <?php $this->msgWiki( $this->data['loggedin'] ? 'createacct-another-realname-tip' : 'prefs-help-realname' ); ?>
-                                       </div>
-                               </div>
-                       <?php } ?>
-
-                       <?php if ( $this->data['usereason'] ) { ?>
-                               <div class="mw-ui-vform-field">
-                                       <label for='wpReason'><?php $this->msg( 'createacct-reason' ); ?></label>
-                                       <?php echo Html::input( 'wpReason', $this->data['reason'], 'text', [
-                                               'class' => 'mw-ui-input loginText',
-                                               'id' => 'wpReason',
-                                               'tabindex' => '8',
-                                               'size' => '20',
-                                               'placeholder' => $this->getMsg( 'createacct-reason-ph' )->text()
-                                       ] ); ?>
-                               </div>
-                       <?php } ?>
-
-                       <?php
-                       $tabIndex = 9;
-                       if ( isset( $this->data['extraInput'] ) && is_array( $this->data['extraInput'] ) ) {
-                               foreach ( $this->data['extraInput'] as $inputItem ) { ?>
-                                       <div class="mw-ui-vform-field">
-                                               <?php
-                                               // If it's a checkbox, output the whole thing (assume it has a msg).
-                                               if ( $inputItem['type'] == 'checkbox' ) {
-                                               ?>
-                                                       <div class="mw-ui-checkbox">
-                                                               <input
-                                                                       name="<?php echo htmlspecialchars( $inputItem['name'] ); ?>"
-                                                                       id="<?php echo htmlspecialchars( $inputItem['name'] ); ?>"
-                                                                       type="checkbox" value="1"
-                                                                       tabindex="<?php echo $tabIndex++; ?>"
-                                                                       <?php if ( !empty( $inputItem['value'] ) ) {
-                                                                               echo 'checked="checked"';
-                                                                       } ?>
-                                                               ><label for="<?php echo htmlspecialchars( $inputItem['name'] ); ?>">
-                                                                       <?php $this->msg( $inputItem['msg'] ); ?>
-                                                               </label>
-                                                       </div>
-                                               <?php
-                                               } else {
-                                                       // Not a checkbox.
-                                                       // TODO (bug 31909) support other input types, e.g. select boxes.
-                                               ?>
-                                                       <?php if ( !empty( $inputItem['msg'] ) ) { ?>
-                                                               <label for="<?php echo htmlspecialchars( $inputItem['name'] ); ?>">
-                                                                       <?php $this->msgWiki( $inputItem['msg'] ); ?>
-                                                               </label>
-                                                       <?php } ?>
-                                                       <input
-                                                               type="<?php echo htmlspecialchars( $inputItem['type'] ); ?>"
-                                                               class="mw-ui-input"
-                                                               name="<?php echo htmlspecialchars( $inputItem['name'] ); ?>"
-                                                               tabindex="<?php echo $tabIndex++; ?>"
-                                                               value="<?php echo htmlspecialchars( $inputItem['value'] ); ?>"
-                                                               id="<?php echo htmlspecialchars( $inputItem['name'] ); ?>"
-                                                       />
-                                               <?php } ?>
-                                               <?php if ( $inputItem['helptext'] !== false ) { ?>
-                                                       <div class="prefsectiontip">
-                                                               <?php $this->msgWiki( $inputItem['helptext'] ); ?>
-                                                       </div>
-                                               <?php } ?>
-                                       </div>
-                               <?php
-                               }
-                       }
-
-                       // A separate placeholder for any inserting any extrafields, e.g used by ConfirmEdit extension
-                       if ( $this->haveData( 'extrafields' ) ) {
-                               echo $this->data['extrafields'];
-                       }
-                       // skip one index.
-                       $tabIndex++;
-                       ?>
-                       <div class="mw-ui-vform-field mw-submit">
-                               <?php
-                               echo Html::submitButton(
-                                       $this->getMsg( $this->data['loggedin'] ? 'createacct-another-submit' : 'createacct-submit' ),
-                                       [
-                                               'id' => 'wpCreateaccount',
-                                               'name' => 'wpCreateaccount',
-                                               'tabindex' => $tabIndex++
-                                       ],
-                                       [
-                                               'mw-ui-block',
-                                               'mw-ui-constructive',
-                                       ]
-                               );
-                               ?>
-                       </div>
-                       <?php if ( $this->haveData( 'uselang' ) ) { ?><input type="hidden" name="uselang" value="<?php $this->text( 'uselang' ); ?>" /><?php } ?>
-                       <?php if ( $this->haveData( 'token' ) ) { ?><input type="hidden" name="wpCreateaccountToken" value="<?php $this->text( 'token' ); ?>" /><?php } ?>
-               </form>
-               <?php if ( !wfMessage( 'signupend' )->isDisabled() ) { ?>
-                       <div id="signupend"><?php $this->html( 'signupend' ); ?></div>
-               <?php } ?>
-       </div>
-       <div class="mw-createacct-benefits-container">
-               <h2><?php $this->msg( 'createacct-benefit-heading' ); ?></h2>
-               <div class="mw-createacct-benefits-list">
-                       <?php
-                       for ( $benefitIdx = 1; $benefitIdx <= $this->data['benefitCount']; $benefitIdx++ ) {
-                               // Pass each benefit's head text (by default a number) as a parameter to the body's message for PLURAL handling.
-                               $headUnescaped = $this->getMsg( "createacct-benefit-head$benefitIdx" )->text();
-                       ?>
-                               <div class="mw-number-text <?php $this->msg( "createacct-benefit-icon$benefitIdx" ); ?>">
-                                       <h3><?php $this->msg( "createacct-benefit-head$benefitIdx" ); ?></h3>
-                                       <p><?php echo $this->getMsg( "createacct-benefit-body$benefitIdx" )->params( $headUnescaped )->escaped(); ?></p>
-                               </div>
-                       <?php } ?>
-               </div>
-       </div>
-</div>
-<?php
-
-       }
-}
diff --git a/includes/templates/Userlogin.php b/includes/templates/Userlogin.php
deleted file mode 100644 (file)
index e816b62..0000000
+++ /dev/null
@@ -1,223 +0,0 @@
-<?php
-// @codingStandardsIgnoreFile
-/**
- * HTML form for user login (since 1.22 with VForm appearance).
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- * @ingroup Templates
- * @deprecated Will be removed when AuthManager lands.
- *   The login form will be generated via HTMLForm.
- */
-
-class UserloginTemplate extends BaseTemplate {
-
-       function execute() {
-               global $wgCookieExpiration;
-               $expirationDays = ceil( $wgCookieExpiration / ( 3600 * 24 ) );
-?>
-<div class="mw-ui-container">
-       <div id="userloginprompt"><?php $this->msgWiki('loginprompt') ?></div>
-       <?php if ( $this->haveData( 'languages' ) ) { ?>
-               <div id="languagelinks">
-                       <p><?php $this->html( 'languages' ); ?></p>
-               </div>
-       <?php } ?>
-       <div id="userloginForm">
-               <form name="userlogin" class="mw-ui-vform" method="post" action="<?php $this->text( 'action' ); ?>">
-                       <?php if ( $this->data['loggedin'] ) { ?>
-                               <div class="warningbox">
-                                       <?php echo $this->getMsg( 'userlogin-loggedin' )->params( $this->data['loggedinuser'] )->parse(); ?>
-                               </div>
-                       <?php } ?>
-                       <section class="mw-form-header">
-                               <?php $this->html( 'header' ); /* extensions such as ConfirmEdit add form HTML here */ ?>
-                       </section>
-
-                       <?php if ( $this->data['message'] ) { ?>
-                               <div class="<?php $this->text( 'messagetype' ); ?>box">
-                                       <?php if ( $this->data['messagetype'] == 'error' ) { ?>
-                                               <strong><?php $this->msg( 'loginerror' ); ?></strong>
-                                               <br />
-                                       <?php } ?>
-                                       <?php $this->html( 'message' ); ?>
-                               </div>
-                       <?php } ?>
-
-                       <?php if ( $this->data['formheader'] ) { ?>
-                               <div class="mw-form-formheader">
-                                       <?php $this->html( 'formheader' ); /* extensions such as MobileFrontend add HTML here */ ?>
-                               </div>
-                       <?php } ?>
-                       <div class="mw-ui-vform-field">
-                               <label for="wpName1">
-                                       <?php
-                                       $this->msg( 'userlogin-yourname' );
-
-                                       if ( $this->data['secureLoginUrl'] ) {
-                                               echo Html::element( 'a', [
-                                                       'href' => $this->data['secureLoginUrl'],
-                                                       'class' => 'mw-ui-flush-right mw-secure',
-                                               ], $this->getMsg( 'userlogin-signwithsecure' )->text() );
-                                       }
-                                       ?>
-                               </label>
-                               <?php
-                               echo Html::input( 'wpName', $this->data['name'], 'text', [
-                                       'class' => 'loginText mw-ui-input',
-                                       'id' => 'wpName1',
-                                       'tabindex' => '1',
-                                       // 'required' is blacklisted for now in Html.php due to browser issues.
-                                       // Keeping here in case that changes.
-                                       'required' => true,
-                                       // Set focus to this field if it's blank.
-                                       'autofocus' => !$this->data['name'],
-                                       'placeholder' => $this->getMsg( 'userlogin-yourname-ph' )->text()
-                               ] );
-                               ?>
-                       </div>
-
-                       <div class="mw-ui-vform-field">
-                               <label for="wpPassword1">
-                                       <?php
-                                       $this->msg( 'userlogin-yourpassword' );
-                                       ?>
-                               </label>
-                               <?php
-                               echo Html::input( 'wpPassword', null, 'password', [
-                                       'class' => 'loginPassword mw-ui-input',
-                                       'id' => 'wpPassword1',
-                                       'tabindex' => '2',
-                                       // Set focus to this field if username is filled in.
-                                       'autofocus' => (bool)$this->data['name'],
-                                       'placeholder' => $this->getMsg( 'userlogin-yourpassword-ph' )->text()
-                               ] );
-                               ?>
-                       </div>
-
-                       <?php
-                       if ( isset( $this->data['usedomain'] ) && $this->data['usedomain'] ) {
-                               $select = new XmlSelect( 'wpDomain', false, $this->data['domain'] );
-                               $select->setAttribute( 'tabindex', 3 );
-                               foreach ( $this->data['domainnames'] as $dom ) {
-                                       $select->addOption( $dom );
-                               }
-                       ?>
-                               <div class="mw-ui-vform-field" id="mw-user-domain-section">
-                                       <label for="wpDomain"><?php $this->msg( 'yourdomainname' ); ?></label>
-                                       <?php echo $select->getHTML(); ?>
-                               </div>
-                       <?php } ?>
-
-                       <?php
-                       if ( $this->haveData( 'extrafields' ) ) {
-                               echo $this->data['extrafields'];
-                       }
-                       ?>
-
-                       <div class="mw-ui-vform-field">
-                               <?php if ( $this->data['canremember'] ) { ?>
-                                       <div class="mw-ui-checkbox">
-                                               <input name="wpRemember" type="checkbox" value="1" id="wpRemember" tabindex="4"
-                                                       <?php if ( $this->data['remember'] ) {
-                                                               echo 'checked="checked"';
-                                                       } ?>
-                                               ><label for="wpRemember">
-                                                       <?php echo $this->getMsg( 'userlogin-remembermypassword' )->numParams( $expirationDays )->escaped(); ?></label>
-                                       </div>
-                               <?php } ?>
-                       </div>
-
-                       <div class="mw-ui-vform-field">
-                               <?php
-                               $attrs = [
-                                       'id' => 'wpLoginAttempt',
-                                       'name' => 'wpLoginAttempt',
-                                       'tabindex' => '6',
-                               ];
-                               $modifiers = [
-                                       'mw-ui-progressive',
-                               ];
-                               echo Html::submitButton( $this->getMsg( 'pt-login-button' )->text(), $attrs, $modifiers );
-                               ?>
-                       </div>
-
-                       <div class="mw-ui-vform-field mw-form-related-link-container" id="mw-userlogin-help">
-                               <?php
-                               echo Html::element(
-                                       'a',
-                                       [
-                                               'href' => Skin::makeInternalOrExternalUrl(
-                                                       wfMessage( 'helplogin-url' )->inContentLanguage()->text()
-                                               ),
-                                       ],
-                                       $this->getMsg( 'userlogin-helplink2' )->text()
-                               );
-                               ?>
-                       </div>
-                       <?php
-
-                       if ( $this->data['useemail'] && $this->data['canreset'] && $this->data['resetlink'] === true ) {
-                               echo Html::rawElement(
-                                       'div',
-                                       [
-                                               'class' => 'mw-ui-vform-field mw-form-related-link-container',
-                                       ],
-                                       Linker::link(
-                                               SpecialPage::getTitleFor( 'PasswordReset' ),
-                                               $this->getMsg( 'userlogin-resetpassword-link' )->escaped()
-                                       )
-                               );
-                       }
-
-                       if ( $this->haveData( 'createOrLoginHref' ) ) {
-                               if ( $this->data['loggedin'] ) { ?>
-                                       <div class="mw-form-related-link-container mw-ui-vform-field">
-                                               <a href="<?php $this->text( 'createOrLoginHref' ); ?>" id="mw-createaccount-join" tabindex="7"><?php $this->msg( 'userlogin-createanother' ); ?></a>
-                                       </div>
-                               <?php } else { ?>
-                                       <div id="mw-createaccount-cta" class="mw-ui-vform-field">
-                                               <?php $this->msg( 'userlogin-noaccount' ); ?><a href="<?php $this->text( 'createOrLoginHref' ); ?>" id="mw-createaccount-join" tabindex="7" class="mw-ui-button"><?php $this->msg( 'userlogin-joinproject' ); ?></a>
-                                       </div>
-                               <?php
-                               }
-                       }
-
-                       // Hidden fields
-                       $fields = '';
-                       if ( $this->haveData( 'uselang' ) ) {
-                               $fields .= Html::hidden( 'uselang', $this->data['uselang'] );
-                       }
-                       if ( $this->haveData( 'token' ) ) {
-                               $fields .= Html::hidden( 'wpLoginToken', $this->data['token'] );
-                       }
-                       if ( $this->data['cansecurelogin'] ) {
-                               $fields .= Html::hidden( 'wpForceHttps', $this->data['stickhttps'] );
-                       }
-                       if ( $this->data['cansecurelogin'] && $this->haveData( 'fromhttp' ) ) {
-                               $fields .= Html::hidden( 'wpFromhttp', $this->data['fromhttp'] );
-                       }
-                       echo $fields;
-
-                       ?>
-               </form>
-       </div>
-</div>
-<?php
-
-       }
-}
index b620132..03c864a 100644 (file)
@@ -944,6 +944,33 @@ abstract class UploadBase {
                return $this->mLocalFile;
        }
 
+       /**
+        * Like stashFile(), but respects extensions' wishes to prevent the stashing.
+        *
+        * Upload stash exceptions are also caught and converted to an error status.
+        *
+        * @since 1.28
+        * @param User $user
+        * @return Status If successful, value is an UploadStashFile instance
+        */
+       public function tryStashFile( User $user ) {
+               $props = $this->mFileProps;
+               $error = null;
+               Hooks::run( 'UploadStashFile', [ $this, $user, $props, &$error ] );
+               if ( $error ) {
+                       if ( !is_array( $error ) ) {
+                               $error = [ $error ];
+                       }
+                       return call_user_func_array( 'Status::newFatal', $error );
+               }
+               try {
+                       $file = $this->doStashFile( $user );
+                       return Status::newGood( $file );
+               } catch ( UploadStashException $e ) {
+                       return Status::newFatal( 'uploadstash-exception', get_class( $e ), $e->getMessage() );
+               }
+       }
+
        /**
         * If the user does not supply all necessary information in the first upload
         * form submission (either by accident or by design) then we may want to
@@ -956,6 +983,7 @@ abstract class UploadBase {
         * which can be passed through a form or API request to find this stashed
         * file again.
         *
+        * @deprecated since 1.28 Use tryStashFile() instead
         * @param User $user
         * @return UploadStashFile Stashed file
         * @throws UploadStashBadPathException
@@ -963,6 +991,16 @@ abstract class UploadBase {
         * @throws UploadStashNotLoggedInException
         */
        public function stashFile( User $user = null ) {
+               return $this->doStashFile( $user );
+       }
+
+       /**
+        * Implementation for stashFile() and tryStashFile().
+        *
+        * @param User $user
+        * @return UploadStashFile Stashed file
+        */
+       protected function doStashFile( User $user = null ) {
                $stash = RepoGroup::singleton()->getLocalRepo()->getUploadStash( $user );
                $file = $stash->stashFile( $this->mTempPath, $this->getSourceType() );
                $this->mLocalFile = $file;
@@ -979,7 +1017,7 @@ abstract class UploadBase {
         */
        public function stashFileGetKey() {
                wfDeprecated( __METHOD__, '1.28' );
-               return $this->stashFile()->getFileKey();
+               return $this->doStashFile()->getFileKey();
        }
 
        /**
@@ -990,7 +1028,7 @@ abstract class UploadBase {
         */
        public function stashSession() {
                wfDeprecated( __METHOD__, '1.28' );
-               return $this->stashFile()->getFileKey();
+               return $this->doStashFile()->getFileKey();
        }
 
        /**
index 0323b68..cc1d698 100644 (file)
@@ -65,19 +65,19 @@ class UploadFromChunks extends UploadFromFile {
        }
 
        /**
-        * Calls the parent stashFile and updates the uploadsession table to handle "chunks"
+        * Calls the parent doStashFile and updates the uploadsession table to handle "chunks"
         *
         * @param User|null $user
         * @return UploadStashFile Stashed file
         */
-       public function stashFile( User $user = null ) {
+       protected function doStashFile( User $user = null ) {
                // Stash file is the called on creating a new chunk session:
                $this->mChunkIndex = 0;
                $this->mOffset = 0;
 
                $this->verifyChunk();
                // Create a local stash target
-               $this->mLocalFile = parent::stashFile( $user );
+               $this->mLocalFile = parent::doStashFile( $user );
                // Update the initial file offset (based on file size)
                $this->mOffset = $this->mLocalFile->getSize();
                $this->mFileKey = $this->mLocalFile->getFileKey();
@@ -162,7 +162,7 @@ class UploadFromChunks extends UploadFromFile {
                // Update the mTempPath and mLocalFile
                // (for FileUpload or normal Stash to take over)
                $tStart = microtime( true );
-               $this->mLocalFile = parent::stashFile( $this->user );
+               $this->mLocalFile = parent::doStashFile( $this->user );
                $tAmount = microtime( true ) - $tStart;
                $this->mLocalFile->setLocalReference( $tmpFile ); // reuse (e.g. for getImageInfo())
                wfDebugLog( 'fileconcatenate', "Stashed combined file ($i chunks) in $tAmount seconds." );
index 908c8aa..50bcbc4 100644 (file)
@@ -153,10 +153,10 @@ class UploadFromStash extends UploadBase {
         * @param User $user
         * @return UploadStashFile
         */
-       public function stashFile( User $user = null ) {
+       protected function doStashFile( User $user = null ) {
                // replace mLocalFile with an instance of UploadStashFile, which adds some methods
                // that are useful for stashed files.
-               $this->mLocalFile = parent::stashFile( $user );
+               $this->mLocalFile = parent::doStashFile( $user );
 
                return $this->mLocalFile;
        }
index 181ff46..7ba1d91 100644 (file)
@@ -648,8 +648,6 @@ class User implements IDBAccessObject {
         * @since 1.27
         */
        public static function newSystemUser( $name, $options = [] ) {
-               global $wgDisableAuthManager;
-
                $options += [
                        'validate' => 'valid',
                        'create' => true,
@@ -662,9 +660,6 @@ class User implements IDBAccessObject {
                }
 
                $fields = self::selectFields();
-               if ( $wgDisableAuthManager ) {
-                       $fields = array_merge( $fields, [ 'user_password', 'user_newpassword' ] );
-               }
 
                $dbw = wfGetDB( DB_MASTER );
                $row = $dbw->selectRow(
@@ -681,49 +676,15 @@ class User implements IDBAccessObject {
 
                // A user is considered to exist as a non-system user if it can
                // authenticate, or has an email set, or has a non-invalid token.
-               if ( !$user->mEmail && $user->mToken === self::INVALID_TOKEN ) {
-                       if ( $wgDisableAuthManager ) {
-                               $passwordFactory = new PasswordFactory();
-                               $passwordFactory->init( RequestContext::getMain()->getConfig() );
-                               try {
-                                       $password = $passwordFactory->newFromCiphertext( $row->user_password );
-                               } catch ( PasswordError $e ) {
-                                       wfDebug( 'Invalid password hash found in database.' );
-                                       $password = PasswordFactory::newInvalidPassword();
-                               }
-                               try {
-                                       $newpassword = $passwordFactory->newFromCiphertext( $row->user_newpassword );
-                               } catch ( PasswordError $e ) {
-                                       wfDebug( 'Invalid password hash found in database.' );
-                                       $newpassword = PasswordFactory::newInvalidPassword();
-                               }
-                               $canAuthenticate = !$password instanceof InvalidPassword ||
-                                       !$newpassword instanceof InvalidPassword;
-                       } else {
-                               $canAuthenticate = AuthManager::singleton()->userCanAuthenticate( $name );
-                       }
-               }
-               if ( $user->mEmail || $user->mToken !== self::INVALID_TOKEN || $canAuthenticate ) {
+               if ( $user->mEmail || $user->mToken !== self::INVALID_TOKEN ||
+                       AuthManager::singleton()->userCanAuthenticate( $name )
+               ) {
                        // User exists. Steal it?
                        if ( !$options['steal'] ) {
                                return null;
                        }
 
-                       if ( $wgDisableAuthManager ) {
-                               $nopass = PasswordFactory::newInvalidPassword()->toString();
-                               $dbw->update(
-                                       'user',
-                                       [
-                                               'user_password' => $nopass,
-                                               'user_newpassword' => $nopass,
-                                               'user_newpass_time' => null,
-                                       ],
-                                       [ 'user_id' => $user->getId() ],
-                                       __METHOD__
-                               );
-                       } else {
-                               AuthManager::singleton()->revokeAccessForUser( $name );
-                       }
+                       AuthManager::singleton()->revokeAccessForUser( $name );
 
                        $user->invalidateEmail();
                        $user->mToken = self::INVALID_TOKEN;
@@ -2508,31 +2469,7 @@ class User implements IDBAccessObject {
         * @return bool
         */
        public function setPassword( $str ) {
-               global $wgAuth, $wgDisableAuthManager;
-
-               if ( !$wgDisableAuthManager ) {
-                       return $this->setPasswordInternal( $str );
-               }
-
-               if ( $str !== null ) {
-                       if ( !$wgAuth->allowPasswordChange() ) {
-                               throw new PasswordError( wfMessage( 'password-change-forbidden' )->text() );
-                       }
-
-                       $status = $this->checkPasswordValidity( $str );
-                       if ( !$status->isGood() ) {
-                               throw new PasswordError( $status->getMessage()->text() );
-                       }
-               }
-
-               if ( !$wgAuth->setPassword( $this, $str ) ) {
-                       throw new PasswordError( wfMessage( 'externaldberror' )->text() );
-               }
-
-               $this->setOption( 'watchlisttoken', false );
-               $this->setPasswordInternal( $str );
-
-               return true;
+               return $this->setPasswordInternal( $str );
        }
 
        /**
@@ -2544,16 +2481,7 @@ class User implements IDBAccessObject {
         *  through the web interface.
         */
        public function setInternalPassword( $str ) {
-               global $wgAuth, $wgDisableAuthManager;
-
-               if ( !$wgDisableAuthManager ) {
-                       $this->setPasswordInternal( $str );
-               }
-
-               if ( $wgAuth->allowSetLocalPassword() ) {
-                       $this->setOption( 'watchlisttoken', false );
-                       $this->setPasswordInternal( $str );
-               }
+               $this->setPasswordInternal( $str );
        }
 
        /**
@@ -2565,55 +2493,26 @@ class User implements IDBAccessObject {
         * @return bool Success
         */
        private function setPasswordInternal( $str ) {
-               global $wgDisableAuthManager;
-
-               if ( $wgDisableAuthManager ) {
-                       $id = self::idFromName( $this->getName(), self::READ_LATEST );
-                       if ( $id == 0 ) {
-                               throw new LogicException( 'Cannot set a password for a user that is not in the database.' );
-                       }
-
-                       $passwordFactory = new PasswordFactory();
-                       $passwordFactory->init( RequestContext::getMain()->getConfig() );
-                       $dbw = wfGetDB( DB_MASTER );
-                       $dbw->update(
-                               'user',
-                               [
-                                       'user_password' => $passwordFactory->newFromPlaintext( $str )->toString(),
-                                       'user_newpassword' => PasswordFactory::newInvalidPassword()->toString(),
-                                       'user_newpass_time' => $dbw->timestampOrNull( null ),
-                               ],
-                               [
-                                       'user_id' => $id,
-                               ],
-                               __METHOD__
-                       );
-
-                       // When the main password is changed, invalidate all bot passwords too
-                       BotPassword::invalidateAllPasswordsForUser( $this->getName() );
-               } else {
-                       $manager = AuthManager::singleton();
-
-                       // If the user doesn't exist yet, fail
-                       if ( !$manager->userExists( $this->getName() ) ) {
-                               throw new LogicException( 'Cannot set a password for a user that is not in the database.' );
-                       }
+               $manager = AuthManager::singleton();
 
-                       $status = $this->changeAuthenticationData( [
-                               'username' => $this->getName(),
-                               'password' => $str,
-                               'retype' => $str,
-                       ] );
-                       if ( !$status->isGood() ) {
-                               \MediaWiki\Logger\LoggerFactory::getInstance( 'authentication' )
-                                       ->info( __METHOD__ . ': Password change rejected: '
-                                               . $status->getWikiText( null, null, 'en' ) );
-                               return false;
-                       }
+               // If the user doesn't exist yet, fail
+               if ( !$manager->userExists( $this->getName() ) ) {
+                       throw new LogicException( 'Cannot set a password for a user that is not in the database.' );
+               }
 
-                       $this->setOption( 'watchlisttoken', false );
+               $status = $this->changeAuthenticationData( [
+                       'username' => $this->getName(),
+                       'password' => $str,
+                       'retype' => $str,
+               ] );
+               if ( !$status->isGood() ) {
+                       \MediaWiki\Logger\LoggerFactory::getInstance( 'authentication' )
+                               ->info( __METHOD__ . ': Password change rejected: '
+                                       . $status->getWikiText( null, null, 'en' ) );
+                       return false;
                }
 
+               $this->setOption( 'watchlisttoken', false );
                SessionManager::singleton()->invalidateSessionsForUser( $this );
 
                return true;
@@ -2632,12 +2531,6 @@ class User implements IDBAccessObject {
         * @since 1.27
         */
        public function changeAuthenticationData( array $data ) {
-               global $wgDisableAuthManager;
-               if ( $wgDisableAuthManager ) {
-                       throw new LogicException( __METHOD__ . ' cannot be called when $wgDisableAuthManager '
-                               . 'is true' );
-               }
-
                $manager = AuthManager::singleton();
                $reqs = $manager->getAuthenticationRequests( AuthManager::ACTION_CHANGE, $this );
                $reqs = AuthenticationRequest::loadRequestsFromSubmission( $reqs, $data );
@@ -2723,32 +2616,7 @@ class User implements IDBAccessObject {
         * @param bool $throttle If true, reset the throttle timestamp to the present
         */
        public function setNewpassword( $str, $throttle = true ) {
-               global $wgDisableAuthManager;
-
-               if ( $wgDisableAuthManager ) {
-                       $id = $this->getId();
-                       if ( $id == 0 ) {
-                               throw new LogicException( 'Cannot set new password for a user that is not in the database.' );
-                       }
-
-                       $dbw = wfGetDB( DB_MASTER );
-
-                       $passwordFactory = new PasswordFactory();
-                       $passwordFactory->init( RequestContext::getMain()->getConfig() );
-                       $update = [
-                               'user_newpassword' => $passwordFactory->newFromPlaintext( $str )->toString(),
-                       ];
-
-                       if ( $str === null ) {
-                               $update['user_newpass_time'] = null;
-                       } elseif ( $throttle ) {
-                               $update['user_newpass_time'] = $dbw->timestamp();
-                       }
-
-                       $dbw->update( 'user', $update, [ 'user_id' => $id ], __METHOD__ );
-               } else {
-                       throw new BadMethodCallException( __METHOD__ . ' has been removed in 1.27' );
-               }
+               throw new BadMethodCallException( __METHOD__ . ' has been removed in 1.27' );
        }
 
        /**
@@ -2758,33 +2626,7 @@ class User implements IDBAccessObject {
         * @return bool
         */
        public function isPasswordReminderThrottled() {
-               global $wgPasswordReminderResendTime, $wgDisableAuthManager;
-
-               if ( $wgDisableAuthManager ) {
-                       if ( !$wgPasswordReminderResendTime ) {
-                               return false;
-                       }
-
-                       $this->load();
-
-                       $db = ( $this->queryFlagsUsed & self::READ_LATEST )
-                               ? wfGetDB( DB_MASTER )
-                               : wfGetDB( DB_SLAVE );
-                       $newpassTime = $db->selectField(
-                               'user',
-                               'user_newpass_time',
-                               [ 'user_id' => $this->getId() ],
-                               __METHOD__
-                       );
-
-                       if ( $newpassTime === null ) {
-                               return false;
-                       }
-                       $expiry = wfTimestamp( TS_UNIX, $newpassTime ) + $wgPasswordReminderResendTime * 3600;
-                       return time() < $expiry;
-               } else {
-                       throw new BadMethodCallException( __METHOD__ . ' has been removed in 1.27' );
-               }
+               throw new BadMethodCallException( __METHOD__ . ' has been removed in 1.27' );
        }
 
        /**
@@ -3926,7 +3768,7 @@ class User implements IDBAccessObject {
                        ScopedCallback::consume( $delay );
                        $error = false;
                }
-               \MediaWiki\Logger\LoggerFactory::getInstance( 'authmanager' )->info( 'Logout', [
+               \MediaWiki\Logger\LoggerFactory::getInstance( 'authevents' )->info( 'Logout', [
                        'event' => 'logout',
                        'successful' => $error === false,
                        'status' => $error ?: 'success',
@@ -4280,87 +4122,27 @@ class User implements IDBAccessObject {
         * @return bool True if the given password is correct, otherwise False
         */
        public function checkPassword( $password ) {
-               global $wgAuth, $wgLegacyEncoding, $wgDisableAuthManager;
-
-               if ( $wgDisableAuthManager ) {
-                       $this->load();
-
-                       // Some passwords will give a fatal Status, which means there is
-                       // some sort of technical or security reason for this password to
-                       // be completely invalid and should never be checked (e.g., T64685)
-                       if ( !$this->checkPasswordValidity( $password )->isOK() ) {
-                               return false;
-                       }
-
-                       // Certain authentication plugins do NOT want to save
-                       // domain passwords in a mysql database, so we should
-                       // check this (in case $wgAuth->strict() is false).
-                       if ( $wgAuth->authenticate( $this->getName(), $password ) ) {
+               $manager = AuthManager::singleton();
+               $reqs = AuthenticationRequest::loadRequestsFromSubmission(
+                       $manager->getAuthenticationRequests( AuthManager::ACTION_LOGIN ),
+                       [
+                               'username' => $this->getName(),
+                               'password' => $password,
+                       ]
+               );
+               $res = AuthManager::singleton()->beginAuthentication( $reqs, 'null:' );
+               switch ( $res->status ) {
+                       case AuthenticationResponse::PASS:
                                return true;
-                       } elseif ( $wgAuth->strict() ) {
-                               // Auth plugin doesn't allow local authentication
-                               return false;
-                       } elseif ( $wgAuth->strictUserAuth( $this->getName() ) ) {
-                               // Auth plugin doesn't allow local authentication for this user name
+                       case AuthenticationResponse::FAIL:
+                               // Hope it's not a PreAuthenticationProvider that failed...
+                               \MediaWiki\Logger\LoggerFactory::getInstance( 'authentication' )
+                                       ->info( __METHOD__ . ': Authentication failed: ' . $res->message->plain() );
                                return false;
-                       }
-
-                       $passwordFactory = new PasswordFactory();
-                       $passwordFactory->init( RequestContext::getMain()->getConfig() );
-                       $db = ( $this->queryFlagsUsed & self::READ_LATEST )
-                               ? wfGetDB( DB_MASTER )
-                               : wfGetDB( DB_SLAVE );
-
-                       try {
-                               $mPassword = $passwordFactory->newFromCiphertext( $db->selectField(
-                                       'user', 'user_password', [ 'user_id' => $this->getId() ], __METHOD__
-                               ) );
-                       } catch ( PasswordError $e ) {
-                               wfDebug( 'Invalid password hash found in database.' );
-                               $mPassword = PasswordFactory::newInvalidPassword();
-                       }
-
-                       if ( !$mPassword->equals( $password ) ) {
-                               if ( $wgLegacyEncoding ) {
-                                       // Some wikis were converted from ISO 8859-1 to UTF-8, the passwords can't be converted
-                                       // Check for this with iconv
-                                       $cp1252Password = iconv( 'UTF-8', 'WINDOWS-1252//TRANSLIT', $password );
-                                       if ( $cp1252Password === $password || !$mPassword->equals( $cp1252Password ) ) {
-                                               return false;
-                                       }
-                               } else {
-                                       return false;
-                               }
-                       }
-
-                       if ( $passwordFactory->needsUpdate( $mPassword ) && !wfReadOnly() ) {
-                               $this->setPasswordInternal( $password );
-                       }
-
-                       return true;
-               } else {
-                       $manager = AuthManager::singleton();
-                       $reqs = AuthenticationRequest::loadRequestsFromSubmission(
-                               $manager->getAuthenticationRequests( AuthManager::ACTION_LOGIN ),
-                               [
-                                       'username' => $this->getName(),
-                                       'password' => $password,
-                               ]
-                       );
-                       $res = AuthManager::singleton()->beginAuthentication( $reqs, 'null:' );
-                       switch ( $res->status ) {
-                               case AuthenticationResponse::PASS:
-                                       return true;
-                               case AuthenticationResponse::FAIL:
-                                       // Hope it's not a PreAuthenticationProvider that failed...
-                                       \MediaWiki\Logger\LoggerFactory::getInstance( 'authentication' )
-                                               ->info( __METHOD__ . ': Authentication failed: ' . $res->message->plain() );
-                                       return false;
-                               default:
-                                       throw new BadMethodCallException(
-                                               'AuthManager returned a response unsupported by ' . __METHOD__
-                                       );
-                       }
+                       default:
+                               throw new BadMethodCallException(
+                                       'AuthManager returned a response unsupported by ' . __METHOD__
+                               );
                }
        }
 
@@ -4373,43 +4155,8 @@ class User implements IDBAccessObject {
         * @return bool True if matches, false otherwise
         */
        public function checkTemporaryPassword( $plaintext ) {
-               global $wgNewPasswordExpiry, $wgDisableAuthManager;
-
-               if ( $wgDisableAuthManager ) {
-                       $this->load();
-
-                       $passwordFactory = new PasswordFactory();
-                       $passwordFactory->init( RequestContext::getMain()->getConfig() );
-                       $db = ( $this->queryFlagsUsed & self::READ_LATEST )
-                               ? wfGetDB( DB_MASTER )
-                               : wfGetDB( DB_SLAVE );
-
-                       $row = $db->selectRow(
-                               'user',
-                               [ 'user_newpassword', 'user_newpass_time' ],
-                               [ 'user_id' => $this->getId() ],
-                               __METHOD__
-                       );
-                       try {
-                               $newPassword = $passwordFactory->newFromCiphertext( $row->user_newpassword );
-                       } catch ( PasswordError $e ) {
-                               wfDebug( 'Invalid password hash found in database.' );
-                               $newPassword = PasswordFactory::newInvalidPassword();
-                       }
-
-                       if ( $newPassword->equals( $plaintext ) ) {
-                               if ( is_null( $row->user_newpass_time ) ) {
-                                       return true;
-                               }
-                               $expiry = wfTimestamp( TS_UNIX, $row->user_newpass_time ) + $wgNewPasswordExpiry;
-                               return ( time() < $expiry );
-                       } else {
-                               return false;
-                       }
-               } else {
-                       // Can't check the temporary password individually.
-                       return $this->checkPassword( $plaintext );
-               }
+               // Can't check the temporary password individually.
+               return $this->checkPassword( $plaintext );
        }
 
        /**
@@ -5286,45 +5033,10 @@ class User implements IDBAccessObject {
         *     - false will be converted to 'create' if this object is the same as
         *       $wgUser and to 'create2' otherwise
         * @param string $reason User supplied reason
-        * @return int|bool True if not $wgNewUserLog or not $wgDisableAuthManager;
-        *   otherwise ID of log item or 0 on failure
+        * @return bool true
         */
        public function addNewUserLogEntry( $action = false, $reason = '' ) {
-               global $wgUser, $wgNewUserLog, $wgDisableAuthManager;
-               if ( !$wgDisableAuthManager || empty( $wgNewUserLog ) ) {
-                       return true; // disabled
-               }
-
-               if ( $action === true ) {
-                       $action = 'byemail';
-               } elseif ( $action === false ) {
-                       if ( $this->equals( $wgUser ) ) {
-                               $action = 'create';
-                       } else {
-                               $action = 'create2';
-                       }
-               }
-
-               if ( $action === 'create' || $action === 'autocreate' ) {
-                       $performer = $this;
-               } else {
-                       $performer = $wgUser;
-               }
-
-               $logEntry = new ManualLogEntry( 'newusers', $action );
-               $logEntry->setPerformer( $performer );
-               $logEntry->setTarget( $this->getUserPage() );
-               $logEntry->setComment( $reason );
-               $logEntry->setParameters( [
-                       '4::userid' => $this->getId(),
-               ] );
-               $logid = $logEntry->insert();
-
-               if ( $action !== 'autocreate' ) {
-                       $logEntry->publish( $logid );
-               }
-
-               return (int)$logid;
+               return true; // disabled
        }
 
        /**
index 2ebc9ed..395ce37 100644 (file)
@@ -11,7 +11,7 @@
  *     $gen = new AutoloadGenerator( __DIR__ );
  *     $gen->readDir( __DIR__ . '/includes' );
  *     $gen->readFile( __DIR__ . '/foo.php' )
- *     $gen->generateAutoload();
+ *     $gen->getAutoload();
  */
 class AutoloadGenerator {
        const FILETYPE_JSON = 'json';
index b414d5e..f511d2b 100644 (file)
@@ -13,7 +13,9 @@
                        "Wōdenhelm",
                        "아라",
                        "Dpk",
-                       "Macofe"
+                       "Macofe",
+                       "WhatamIdoing",
+                       "Hogweard"
                ]
        },
        "tog-underline": "Mearc under hlencan:",
        "october-date": "$1. Winterfylleðes",
        "november-date": "$1. Blōtmōnaðes",
        "december-date": "$1. Ǣrran Gēolan",
+       "period-am": "on undernmǣl",
+       "period-pm": "on ofernōn",
        "pagecategories": "{{PLURAL:$1|Flocc|Floccas}}",
        "category_header": "Trametas in \"$1\" flocce",
        "subcategories": "Underfloccas",
        "jumptonavigation": "þurhfōr",
        "jumptosearch": "sēcan",
        "view-pool-error": "Wālā, þā þegntōlas nū oferlīce wyrcaþ.\nTō mænige brūcendas gesēcaþ tō sēonne þisne tramet.\nWē biddaþ þæt þū abīde scortne tīman ǣr þū gesēce to sēonne þisne tramet eft.\n\n$1",
+       "pool-queuefull": "Pundfaldes forepenn is full",
        "pool-errorunknown": "Uncūþ wōh",
+       "pool-servererror": "Seo pundaldgetalere þēgnung nis gearo",
        "aboutsite": "Gecȳþness ymbe {{GRAMMAR:wrēgendlīc|{{SITENAME}}}}",
        "aboutpage": "Project:Gefrǣge",
        "copyright": "Man mæg innunge under $1 findan, būton þǣr hit is elles amearcod.",
        "minoredit": "Þēos is lytel adihtung",
        "watchthis": "Behealdan þisne tramet",
        "savearticle": "Hordian tramet",
+       "publishchanges": "Geswutele wrixlung",
        "preview": "Forebysen",
        "showpreview": "Īwan forebysene",
        "showdiff": "Īwan andwendunga",
index 9b4447b..5e8b4b2 100644 (file)
        "createacct-email-ph": "أدخل عنوان بريدك الإلكتروني",
        "createacct-another-email-ph": "أدخل عنوان البريد الإلكتروني",
        "createaccountmail": "استخدم كلمة سر عشوائية مؤقتة وارسلها إلى عنوان البريد الإلكتروني المحدد أدناه",
+       "createaccountmail-help": "يمكن استخدامه لإنشاء حساب لشخص آخر من دون معرفة كلمة المرور.",
        "createacct-realname": "الاسم الحقيقي (اختياري)",
        "createaccountreason": "السبب:",
        "createacct-reason": "السبب",
        "createacct-reason-ph": "لماذا تقوم بإنشاء حساب آخر",
+       "createacct-reason-help": "رسالة تظهر في سجل إنشاء الحسابات",
        "createacct-submit": "افتح الحساب",
        "createacct-another-submit": "أنشئ حسابا",
        "createacct-continue-submit": "مواصلة إنشاء الحساب",
        "passwordreset-emailelement": "اسم {{GENDER:$1\n|المستخدم|المستخدمة}}: \n$1\n\nكلمة السر المؤقتة: \n$2",
        "passwordreset-emailsentemail": "إذا كان هذا العنوان البريد مرتبط بحسابك، من ثم سيتم إرسال بريد إلكتروني لإعادة تعيين كلمة السر.",
        "passwordreset-emailsentusername": "إذا كان هناك عنوان بريد إلكتروني مرتبط بهذا المستخدم، ثم سيتم إرسال بريد إلكتروني لإعادة تعيين كلمة السر.",
-       "passwordreset-emailsent-capture": "أُرسل بريد إلكتروني لإعادة ضبط كلمة السر، وهو معروض بالأسفل.",
-       "passwordreset-emailerror-capture": "تم توليد رسالة بريد إلكتروني لتصفير كلمة السر نصّه التالي، إلا أنه تعذّر إرسال الرّسالة إلى {{GENDER:$2|المستخدم|المستخدمة}}: $1",
        "passwordreset-invalideamil": "عنوان بريد إلكتروني غير صالح",
        "changeemail": "تغيير أو إزالة عنوان البريد الإلكتروني",
        "changeemail-header": "إكمال هذا النموذج لتغيير عنوان البريد الإلكتروني الخاص بك. إذا كنت ترغب في إزالة جمعية أي عنوان البريد الإلكتروني من حسابك، وترك الفراغ عنوان البريد الإلكتروني الجديد عند تقديم النموذج",
-       "changeemail-passwordrequired": "تحتاج إلى إدخال كلمة السر الخاصة بك لتأكيد هذا التغيير.",
        "changeemail-no-info": "يجب تسجيل الدخول للوصول إلى هذه الصفحة مباشرة.",
        "changeemail-oldemail": "عنوان البريد الإلكتروني الحالي:",
        "changeemail-newemail": "عنوان البريد الإلكتروني الجديد:",
        "undo-nochange": "التعديل يبدو أنه قد تم الترجع عنه بالفعل.",
        "undo-summary": "الرجوع عن التعديل $1 بواسطة [[Special:Contributions/$2|$2]] ([[User talk:$2|نقاش]])",
        "undo-summary-username-hidden": "الرجوع عن المراجعة $1 التي أجراها مستخدمي مخفي",
-       "cantcreateaccounttitle": "لا يمكن إنشاء حساب",
        "cantcreateaccount-text": "إنشاء الحسابات من عنوان الأيبي هذا ('''$1''') تم منعه بواسطة [[User:$3|$3]].\n\nالسبب المعطى بواسطة $3 هو ''$2''",
        "cantcreateaccount-range-text": "إنشاء الحسابات من عناوين الآيبي في النطاق <strong>$1</strong>، التي تحتوي على الآيبي الخاص بك (<strong>$4</strong>)، قد منعها [[User:$3|$3]].\n\nالسبب المعطى بواسطة $3 هو <em>$2</em>",
        "viewpagelogs": "اعرض سجلات هذه الصفحة",
        "undeletedrevisions-files": "أسترجعت {{PLURAL:$1||مراجعة واحدة|مراجعتان|$1 مراجعات|$1 مراجعة}}  و{{PLURAL:$2||ملف واحد|ملفان|$2 ملفات|$2 ملفًا|$2 ملف}}",
        "undeletedfiles": "أسترجع {{PLURAL:$1||ملف واحد|ملفان|$1 ملفات|$1 ملفًا|$1 ملف}}",
        "cannotundelete": "فشل الاسترجاع؛\n$1",
-       "undeletedpage": "'''تÙ\85 Ø§Ø³ØªØ±Ø¬Ø§Ø¹ $1'''\n\nراجع [[Special:Log/delete|سجÙ\84 Ø§Ù\84حدف]] لمعاينة عمليات الحذف والاسترجاعات الحديثة.",
+       "undeletedpage": "'''تÙ\85 Ø§Ø³ØªØ±Ø¬Ø§Ø¹ $1'''\n\nراجع [[Special:Log/delete|سجÙ\84 Ø§Ù\84حذف]] لمعاينة عمليات الحذف والاسترجاعات الحديثة.",
        "undelete-header": "انظر الصفحات المحذوفة حديثا في [[Special:Log/delete|سجل الحذف]].",
        "undelete-search-title": "البحث في الصفحات المحذوفة",
        "undelete-search-box": "ابحث في الصفحات المحذوفة",
        "ipb-unblock": "رفع المنع عن مستخدم أو عنوان أيبي",
        "ipb-blocklist": "عرض حالات المنع الحالية",
        "ipb-blocklist-contribs": "مساهمات $1",
+       "ipb-blocklist-duration-left": "يتبقى $1",
        "unblockip": "رفع المنع عن المستخدم",
        "unblockiptext": "استخدم الاستمارة أدناه لاسترجاع صلاحية الكتابة الخاصة بعنوان أيبي أو مستخدم تم سحبها منه مسبقا.",
        "ipusubmit": "ارفع هذا المنع",
        "lockdbsuccesstext": "لقد أغلقت قاعدة البيانات.<br />\nتذكر أن [[Special:UnlockDB|تزيل الغلق]] بعد اكتمال أعمال الصيانة.",
        "unlockdbsuccesstext": "تم إعادة فتح قاعدة البيانات",
        "lockfilenotwritable": "ملف غلق قاعدة البيانات لا يمكن الكتابة عليه.\nلغلق قاعدة البيانات أو إزالة الغلق يجب أن يكون هذا الملف قابلاً للكتابة من قبل خادوم الويب.",
+       "databaselocked": "قاعدة البيانات مقفلة بالفعل.",
        "databasenotlocked": "قاعدة البيانات ليست مغلقة.",
        "lockedbyandtime": "(من $1 على $2 في $3 )",
        "move-page": "نقل $1",
        "confirm-watch-top": "إضافة هذه الصفحة إلى قائمة مراقبتك؟",
        "confirm-unwatch-button": "موافق",
        "confirm-unwatch-top": "إزالة هذه الصفحة من قائمة مراقبتك؟",
+       "confirm-rollback-button": "موافق",
        "semicolon-separator": "؛&#32;",
        "comma-separator": "،&#32;",
        "quotation-marks": "«$1»",
        "log-action-filter-upload-overwrite": "إعادة الرفع",
        "authmanager-create-disabled": "إنشاء الحسابات معطل.",
        "authmanager-create-from-login": "لإنشاء حساب، برجاء ملء الحقول أدناه.",
+       "authmanager-retype-help": "كلمة المرور مرة أخرى للتأكيد.",
        "authmanager-email-label": "البريد الإلكتروني",
        "authmanager-email-help": "عنوان البريد الإلكتروني",
        "authmanager-realname-label": "الاسم الحقيقي",
index 8f881e0..0e51642 100644 (file)
        "undo-failure": "الرجوع فى التعديل ما نفعش علشان فى تعديلات متعاكسة حصلت فى الصفحة.",
        "undo-norev": "الرجوع فى التعديل ما نفعش علشان هو يا إما مش موجود أو انه إتمسح.",
        "undo-summary": "الرجوع فى التعديل $1 بتاع [[Special:Contributions/$2|$2]] ([[User talk:$2|نقاش]])",
-       "cantcreateaccounttitle": "مش ممكن فتح حساب",
        "cantcreateaccount-text": "فتح الحسابات من عنوان الأيبى دا ('''$1''') منعه [[User:$3|$3]].\n\nالسبب إللى إداه $3 هو ''$2''",
        "viewpagelogs": "عرض السجلات للصفحه دى",
        "nohistory": "الصفحة دى ما لهاش تاريخ تعديل.",
index 7325d39..0b4a793 100644 (file)
        "passwordreset-emailelement": "Nome d'usuariu: \n$1\n\nContraseña temporal: \n$2",
        "passwordreset-emailsentemail": "Si esta direición de corréu electrónicu ta asociada cola to cuenta, unviaráse un corréu pa reaniciar la contraseña.",
        "passwordreset-emailsentusername": "Si hai una direición de corréu electrónicu asociada con esti nome d'usuariu, unviaráse un corréu electrónicu pa reaniciar la contraseña.",
-       "passwordreset-emailsent-capture": "Unvióse un corréu electrónicu pa reaniciar la contraseña, que s'amuesa abaxo.",
-       "passwordreset-emailerror-capture": "Unvióse un corréu electrónicu pa reaniciar la contraseña, que s'amuesa abaxo, pero falló l'unviu {{GENDER:$2|al usuariu|a la usuaria}}: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|Unvióse'l corréu|Unviáronse los correos}} de reaniciu de contraseña. {{PLURAL:$1|El nome d'usuariu y la contraseña|La llista de nomes d'usuarios y contraseñes}} amuésase de siguío.",
        "passwordreset-emailerror-capture2": "Nun foi posible mandar un corréu electrónicu {{Gender:$2|al usuariu|a la usuaria}}: $1 {{PLURAL:$3|El nome d'usuariu y la contraseña|La llista de nomes d'usuarios y contraseñes}} amuésase de siguío.",
        "passwordreset-nocaller": "Tien d'apurrise un llamador",
        "passwordreset-nodata": "Nun s'apurrió nin un nome d'usuariu nin una dirección de corréu electrónicu",
        "changeemail": "Camudar o desaniciar la dirección de corréu electrónicu",
        "changeemail-header": "Completa esti formulariu pa camudar la dirección de corréu electrónicu. Si quies desaniciar l'asociación de cualquier dirección de corréu electrónicu de la to cuenta, dexa en blancu la nueva dirección de corréu electrónicu cuando unvies el formulariu.",
-       "changeemail-passwordrequired": "Vas tener qu'escribir la contraseña pa confirmar esti cambéu.",
        "changeemail-no-info": "Tien d'aniciar sesión pa entrar direutamente a esta páxina.",
        "changeemail-oldemail": "Direición de corréu electrónicu actual:",
        "changeemail-newemail": "Direición de corréu electrónicu nueva:",
        "undo-nochange": "Paez que la edición yá ta desfecha.",
        "undo-summary": "Esfacer la revisión $1 de [[Special:Contributions/$2|$2]] ([[User talk:$2|alderique]])",
        "undo-summary-username-hidden": "Desfacer la revisión $1 d'un usuariu tapecíu",
-       "cantcreateaccounttitle": "Nun pue crease la cuenta",
        "cantcreateaccount-text": "[[User:$3|$3]] bloquió la creación de cuentes dende esta direición IP (<strong>$1</strong>).\n\nEl motivu dau por $3 ye <em>$2</em>",
        "cantcreateaccount-range-text": "La creación de cuentes dende direiciones IP del rangu <strong>$1</strong>, qu'incluye la so direición IP (<strong>$4</strong>), ta bloquiada pol usuariu [[User:$3|$3]].\n\nLa razón dada por $3 ye <em>$2</em>.",
        "viewpagelogs": "Ver los rexistros d'esta páxina",
        "action-applychangetags": "aplicar etiquetes xunto colos cambios",
        "action-changetags": "amestar y desaniciar etiquetes arbitraries en revisiones individuales y entraes del rexistru",
        "action-deletechangetags": "desaniciar etiquetes de la base de datos",
+       "action-purge": "purgar esta páxina",
        "nchanges": "{{PLURAL:$1|un cambiu|$1 cambios}}",
        "enhancedrc-since-last-visit": "$1 {{PLURAL:$1|dende la última visita}}",
        "enhancedrc-history": "historial",
        "watchnologin": "Non identificáu",
        "addwatch": "Amestar a la llista de siguimientu",
        "addedwatchtext": "«[[:$1]]» y la so páxina d'alderique amestáronse a la to [[Special:Watchlist|llista de siguimientu]].",
+       "addedwatchtext-talk": "«[[:$1]]» y la so páxina asociada amestáronse a la to [[Special:Watchlist|llista de siguimientu]].",
        "addedwatchtext-short": "Amestóse la páxina «$1» a la to llista de siguimientu.",
        "removewatch": "Desaniciar de la llista de siguimientu",
        "removedwatchtext": "«[[:$1]]» y la so páxina d'alderique desaniciáronse de la to [[Special:Watchlist|llista de siguimientu]].",
+       "removedwatchtext-talk": "«[[:$1]]» y la so páxina asociada desaniciáronse de la to [[Special:Watchlist|llista de siguimientu]].",
        "removedwatchtext-short": "Desanicióse la páxina «$1» de la to llista de siguimientu.",
        "watch": "Vixilar",
        "watchthispage": "Vixilar esta páxina",
        "undeletedrevisions": "{{PLURAL:$1|1 revisión restaurada|$1 revisiones restauraes}}",
        "undeletedrevisions-files": "{{PLURAL:$1|1 revisión|$1 revisiones}} y {{PLURAL:$2|1 archivu|$2 archivos}} restauraos",
        "undeletedfiles": "{{PLURAL:$1|1 archivu restauráu|$1 archivos restauraos}}",
-       "cannotundelete": "Falló la restauración:\n$1",
+       "cannotundelete": "Falló total o parcialmente la restauración:\n$1",
        "undeletedpage": "'''Restauróse $1'''\n\nConsulta'l [[Special:Log/delete|rexistru d'esborraos]] pa ver los esborraos y restauraciones de recién.",
        "undelete-header": "Mira nel [[Special:Log/delete|rexistru d'esborraos]] les páxines esborraes recién.",
        "undelete-search-title": "Buscar páxines desaniciaes",
        "sp-contributions-newbies-sub": "Namái les cuentes nueves",
        "sp-contributions-newbies-title": "Contribuciones d'usuariu pa cuentes nueves",
        "sp-contributions-blocklog": "rexistru de bloqueos",
-       "sp-contributions-suppresslog": "collaboraciones del usuariu desaniciaes",
-       "sp-contributions-deleted": "Contribuciones d'usuariu desaniciaes",
+       "sp-contributions-suppresslog": "collaboraciones {{GENDER:$1|del usuariu|de la usuaria}} suprimíes",
+       "sp-contributions-deleted": "collaboraciones {{GENDER:$1|del usuariu|de la usuaria}} desaniciaes",
        "sp-contributions-uploads": "xubes",
        "sp-contributions-logs": "rexistros",
        "sp-contributions-talk": "alderique",
        "authform-notoken": "Falta token",
        "authform-wrongtoken": "Token incorreutu",
        "specialpage-securitylevel-not-allowed-title": "Nun ta permitío",
+       "authpage-cannot-login": "Nun pudo empecipiase l'aniciu de sesión.",
+       "authpage-cannot-login-continue": "Nun pudo siguise col aniciu de sesión. Probablemente la sesión caducó.",
+       "authpage-cannot-create": "Nun pudo empecipiase la creación de la cuenta.",
        "cannotauth-not-allowed-title": "Permisu refugáu",
        "cannotauth-not-allowed": "Nun tienes permisu pa usar esta páxina",
        "credentialsform-account": "Nome de la cuenta:",
index 16bf5bc..026c3f8 100644 (file)
        "minoredit": "Kiçik redaktə",
        "watchthis": "Bu səhifəni izlə",
        "savearticle": "Səhifəni qeyd et",
+       "publishpage": "Səhifəni yayımla",
+       "publishchanges": "Dəyişiklikləri yayımla",
        "preview": "Sınaq görüntüsü",
        "showpreview": "Sınaq göstərişi",
        "showdiff": "Dəyişiklikləri göstər",
        "undo-failure": "Dəyişikliklərin toqquşması nəticəsində geriyə qaytarma işi uğursuz oldu.",
        "undo-norev": "Düzəlişlər geri qaytarıla bilinmir, çünki onlar ya mövcüd deyil, ya da silinib.",
        "undo-summary": "$1 dəyişikliyi [[Special:Contributions/$2|$2]] ([[User talk:$2|Müzakirə]]) tərəfindən geri alındı.",
-       "cantcreateaccounttitle": "Hesab açılmır.",
        "cantcreateaccount-text": "Bu IP ünvanından ('''$1''') istifadəçi hesabı yaradılması [[User:$3|$3]] tərəfindən əngəllənmişdir.\n\n$3 tərəfindən verilən səbəb ''$2''",
        "viewpagelogs": "Bu səhifə ilə bağlı qeydlərə bax",
        "nohistory": "Bu səhifənin dəyişikliklər tarixçəsi mövcud deyil.",
        "unwatching": "İzlənilmir...",
        "enotif_reset": "Baxılmış bütün səhifələri işarələ.",
        "enotif_impersonal_salutation": "{{SITENAME}} istifadəçisi",
+       "enotif_subject_moved": "{{SITENAME}} səhifəsi $1 $2 tərəfindən {{GENDER:$2|köçürüldü}}.",
+       "enotif_subject_changed": "{{SITENAME}} səhifəsi $1 $2 tərəfindən {{GENDER:$2|dəyişdirildi}}.",
        "enotif_body_intro_moved": "{{SITENAME}}da  $1 səhifəsinin adı $PAGEEDITDATE tarixində $2 tərəfindən {{GENDER:$2|dəyişdirilib}}, son versiya üçün bura baxın: $3.",
        "enotif_lastvisited": "Sonuncu ziyarətinizdən indiyədək olan bütün dəyişiklikləri görmək üçün baxın: $1.",
        "enotif_lastdiff": "Bu dəyişikliyi görmək üçün $1 səhifəsinə baxın.",
index abdc239..c2a09db 100644 (file)
        "passwordreset-emailtext-user": "{{SITENAME}} سایتیندا، $1 ایستیفاده‌چی، سیزین اوردا ($4) حسابینیزین رمزینی یئنیله‌مک ایستگی وئریب‌دیر. آشاغیداکی {{PLURAL:$3|ایستیفاده‌چی|ایستیفاده‌چیلر}} بو ایمیل ایله ایلگیلیدیرلر:\n\n$2\n\nبو گئچیجی {{PLURAL:$3|رمز|رمزلر}}، {{PLURAL:$5|بیر|$5گون}} سونرا واختلاری قورتاراجاق‌دیر. \nسیز گرک ایندی گیریب و بیر یئنی رمز سئچه‌سینیز. باشقا آدام بو ایستَگی وئرمیش‌سه، یوخسا سیز اسکی رمزینیزی یادا گتیرمیشسینیزسه، و داها اونو چئویرمک ایسته‌میرسینیزسه، بو مئساژی سایماییب و اسکی رمزینیزی ایشلدمگه داوام ائده بیلرسینیز.",
        "passwordreset-emailelement": "ایشلدن آدی: \n$1\n\nگئچیجی رمز: \n$2",
        "passwordreset-emailsentemail": "بۇ ایمئیل آدرسی حسابینیزا ثبت اوْلونموشسا٬ بیر رمز یئنیله‌مه ایمئیلی گؤندریله‌جکدیر.",
-       "passwordreset-emailsent-capture": "آشاغیدا گؤستریلن کیمی بیر رمز یئنیله‌مه ایمیلی گؤندریلیب‌دیر.",
-       "passwordreset-emailerror-capture": "آشاغیدا گؤستریلن کیمی بیر رمز یئنیله‌مه ایمیلی یارادیلیب‌دیر، اما {{GENDER:$2ایستیفاده‌چی}}‌یه گؤندرمگی باشاریلی اولمادی: $1",
        "changeemail": "ایمیل آدرسینی دَییشدیر یا سیل",
        "changeemail-header": "ایمیل آدرسیزی دَییشدیرمک اوچون بو فورمو دولدورون. حسابیزا بوتون ایمیل‌لرین ارتباطینی کسمک اوچون، یئنی ایمیل آدرسینی بوش ساخلایین.",
-       "changeemail-passwordrequired": "بو دَییشمه‌نی دوغرولاماق اوچون، رمزینیزی یازمالیسیز.",
        "changeemail-no-info": "بو صحیفه‌نی دوغرو گؤردوگونوز اوچون سیستمه گیرمه‌لیسینیز.",
        "changeemail-oldemail": "ایندیکی ایمیل آدرس:",
        "changeemail-newemail": "یئنی ایمیل آدرسی:",
        "watchthis": "بو صفحه‌نی ایزله",
        "savearticle": "صفحه‌نی ذخیره ائت",
        "savechanges": "دَییشیکلیکلری ذخیره ائت",
-       "publishchanges": "دَییشیکلیکلری یای",
+       "publishpage": "صفحه‌نی یاییملا",
+       "publishchanges": "دَییشیک‌لیک‌لری یاییملا",
        "preview": "اؤن‌گؤستریش",
        "showpreview": "سیناق گؤستریش",
        "showdiff": "دَییشیکلیکلری گؤستر",
        "undo-nochange": "نظره گلیر دَییشدیرمه قاباغجادان قایتاریلیب.",
        "undo-summary": "$1 دییشیک‌لیک [[Special:Contributions/$2|$2]] ([[User talk:$2|دانیشیق]]) طرفین‌دن قایتاریلدی.",
        "undo-summary-username-hidden": "گیزلی ایستیفاده‌چی ایله ائدیلمیش $1 نوسخه‌سینی قایتارماق",
-       "cantcreateaccounttitle": "حساب یارادماق اولمور",
        "cantcreateaccount-text": "بو ای پی عنوانین‌دان ('$1) ایستیفاده‌چی حسابی یارادیلماسی [[User:$3|$3]] طرفین‌دن انگللنمیش‌دیر.\n\n$3 طرفین‌دن وئریلن سبب '$2",
        "cantcreateaccount-range-text": "<strong>$1</strong> آی‌پی آدرس آرالیغیندان حساب یارانماق، [[User:$3|$3]] ایشلدنی طرفیندن یاساقلانیب‌دیر. سیزین‌ده آی‌پی آدرسیز (<strong>$4</strong>) بو آرادادیر.\n\n$3 طرفین‌دن وئریلن سبب بودور: «$2»",
        "viewpagelogs": "بۇ صفحه‌نین قئیدلرینه باخ",
        "emailuser": "بو ایستیفاده‌چی‌یه ایمیل گؤندر",
        "emailuser-title-target": "بو {{GENDER:$1|ایستیفاده‌چی}}‌یه ایمیل گؤندر",
        "emailuser-title-notarget": "ایستیفاده‌چی‌یه ایمیل گؤندر",
-       "emailpagetext": "آشغÛ\8cداکÛ\8c Ù\81Ù\88رÙ\85â\80\8cداÙ\86Ø\8c Ø¨Ù\88 {{GENDER:$1|اÛ\8cستÛ\8cÙ\81ادÙ\87â\80\8cÚ\86Û\8c}}â\80\8cÛ\8cÙ\87 Ø§Û\8cÙ\85Û\8cÙ\84 Ú¯Ø¤Ù\86درÙ\85Ú© Ø§Ù\88Ú\86Ù\88Ù\86 Ø§Û\8cستÛ\8cÙ\81ادÙ\87 Ø§Ø¦Ø¯Ù\87 Ø¨Û\8cÙ\84رسÛ\8cÙ\86Û\8cز.\n[[Special:Preferences|اؤز ØªØ±Ø¬Û\8cØ­Ù\84رÛ\8cÙ\86Û\8cز]]دÙ\87 Ù\88ئرÙ\86 Ø§Û\8cÙ\85Û\8cÙ\84 Ø¢Ø¯Ø±Ø³Û\8cØ\8c Ø¨Ù\88 Ø§Û\8cÙ\85Û\8cÙ\84Û\8cÙ\86 \"From\" Û\8cئرÛ\8cÙ\86دÙ\87 Ú¯Ø¤Ø³ØªØ±Û\8cÙ\84Ù\87â\80\8cجکâ\80\8cدÛ\8cر Ù\88 Ø¨Ù\88Ù\86ا Ú¯Ø¤Ø±Ù\87 Ø§Û\8cÙ\85یلی آلان سیزه موستقیم جاواب گؤندره بیلر.",
+       "emailpagetext": "آشاغÛ\8cداکÛ\8c Ù\81Ù\88رÙ\85داÙ\86Ø\8c Ø¨Ù\88 {{GENDER:$1|اÛ\8cستÛ\8cÙ\81ادÙ\87â\80\8cÚ\86Û\8c}}â\80\8cÛ\8cÙ\87 Ø§Û\8cÙ\85ئÛ\8cÙ\84 Ú¯Ø¤Ù\86درÙ\85Ú© Ø§Û\86Ú\86Ù\88Ù\86 Ø§Û\8cستÛ\8cÙ\81ادÙ\87 Ø§Ø¦Ø¯Ù\87 Ø¨Û\8cÙ\84رسÛ\8cÙ\86Û\8cز.\n[[Special:Preferences|اؤز ØªØ±Ø¬Û\8cØ­Ù\84رÛ\8cÙ\86Û\8cز]]دÙ\87 Ù\88ئرÙ\86 Ø§Û\8cÙ\85ئÛ\8cÙ\84 Ø¢Ø¯Ø±Ø³Û\8cØ\8c Ø¨Ù\88 Ø§Û\8cÙ\85ئÛ\8cÙ\84Û\8cÙ\86 \"From\" Û\8cئرÛ\8cÙ\86دÙ\87 Ú¯Ø¤Ø³ØªØ±Û\8cÙ\84Ù\87â\80\8cرک Ø§Û\8cÙ\85ئیلی آلان سیزه موستقیم جاواب گؤندره بیلر.",
        "defemailsubject": "«$1» آدلی ایستیفاده‌چی‌دن، {{SITENAME}} ایمیلی",
        "usermaildisabled": "ایستیفاده‌چی ایمیلی باغلی‌دیر",
        "usermaildisabledtext": "بو ویکی‌ده باشقا ایستیفاده‌چیلره ایمیل گؤندره بیلنمه‌سینیز",
index 84abebd..1dd05c7 100644 (file)
        "tagline": "{{SITENAME}} проектынан",
        "help": "Белешмә",
        "search": "Эҙләү",
-       "search-ignored-headings": " #<!-- был юлды нисек бар шулай ҡалдырығыҙ --> <pre>\n# Эҙләүҙәр инҡар иткән атамалар.\n# Атамаһы булған бит индексланғас та үҙгәртмәләр үҙ көсөнә инәсәк.\n# Буш төҙәтеү менән һеҙ битте яңынан индекслата алаһығыҙ\n# Синтаксис шулай күренә:\n#   * Ошо символға «#» башланған юлдың аҙағына тиклем комментарий була\n#   * Һәр буш булмаған юл - инҡар ителгәндең атамаһы, быға регистр ҙа инә\nИҫкәрмәләр\nҺылтанмалар\nҠарағыҙ шулай уҡ\n#</pre> <!-- был юлды шул көйө ҡалдырығыҙ -->",
+       "search-ignored-headings": " #<!-- был юлды нисек бар шулай ҡалдырығыҙ --> <pre>\n# Эҙләүҙәр инҡар иткән атамалар.\n# Атамаһы булған бит индексланғас та, үҙгәртмәләр үҙ көсөнә инәсәк.\n# Буш төҙәтеү менән һеҙ битте яңынан индекслата алаһығыҙ\n# Синтаксис шулай күренә:\n#   * Ошо символға «#» башланған юлдың аҙағына тиклем комментарий була\n#   * Һәр буш булмаған юл - инҡар ителгәндең атамаһы, быға регистр ҙа инә\nИҫкәрмәләр\nҺылтанмалар\nҠарағыҙ шулай уҡ\n#</pre> <!-- был юлды шул көйө ҡалдырығыҙ -->",
        "searchbutton": "Эҙләү",
        "go": "Күсеү",
        "searcharticle": "Күсеү",
        "passwordreset-emailelement": "Ҡулланыусы исеме: \n$1\n\nВаҡытлыса серһүҙ: \n$2",
        "passwordreset-emailsentemail": "Серһүҙҙе ташлау тураһындағы мәғлүмәт менән электрон почта аша хат ебәрелде.",
        "passwordreset-emailsentusername": "Әгәр был ҡатнашыусының исеменә бәйле  электрон почтаһының адресы булһа, ул саҡта  серһүҙҙе тергеҙеү өсөн  хат ебәреләсәк.",
-       "passwordreset-emailsent-capture": "Серһүҙҙе ташлау тураһындағы мәғлүмәт менән электрон хат ебәрелде, уның тексы түбәндә бирелә:",
-       "passwordreset-emailerror-capture": "Серһүҙҙе ташлау тураһында хәбәр итеүсе электрон хат булдырылғайны, ләкин уны  {{GENDER:$2|kullanıcıya}} түбәндәге сәбәп арҡаһында ебәреп булманы: $1",
        "passwordreset-invalideamil": "Электрон почта адресы ҡабул ителмәй",
        "changeemail": "Электрон почта адресын үҙгәртергә",
        "changeemail-header": "Электрон почта адресын үҙгәртеү",
-       "changeemail-passwordrequired": "Әлеге үҙгәрештәрҙе раҫлау өсөн, Һеҙгә ҡулланыусының серһүҙен яҙырға кәрәк",
        "changeemail-no-info": "Был биткә туранан ирешеү өсөн һеҙгә системала танылыу кәрәк.",
        "changeemail-oldemail": "Хәҙерге электрон почта адресы:",
        "changeemail-newemail": "Яңы электрон почта адресы:",
        "undo-nochange": "Төҙәтеү кире ҡайтарылған.",
        "undo-summary": "[[Special:Contributions/$2|$2]] ҡулланыусыһының ([[User talk:$2|фекер алышыу]]) $1 үҙгәртеүенән баш тартыу",
        "undo-summary-username-hidden": "Исеме йәшерелгән ҡатнашыусының төҙәтеүен  $1 кире ҡағыу",
-       "cantcreateaccounttitle": "Иҫәп яҙыуын яһап булмай",
        "cantcreateaccount-text": "Был IP-адрестан (<b>$1</b>) иҫәп яҙыуҙары булдырыу [[User:$3|$3]] тарафынан тыйылған.\n\n$3 белдергән сәбәп: ''$2''",
        "cantcreateaccount-range-text": "{{GENDER:$3|Ҡатнашыусы}} [[User:$3|$3]] һеҙҙең IP-адрес ингән (<strong>$4</strong>) <strong>$1</strong> диапозонында иҫәп яҙмаһын булдырмаҫҡа {{GENDER:$3|тыйыу}} ҡуйҙы.\n\nОшо сәбәп күһәтелгән: $2.",
        "viewpagelogs": "Был биттең яҙмаларын ҡарарға",
index 2eba576..fceddbc 100644 (file)
@@ -16,7 +16,8 @@
                        "아라",
                        "Matthias Klostermayr",
                        "Macofe",
-                       "George Animal"
+                       "George Animal",
+                       "Lokal Profil"
                ]
        },
        "tog-underline": "Links unterstreichen:",
        "accountcreated": "Benytzerkonto is erstöid worn",
        "accountcreatedtext": "'s Benytzerkonto $1 is aigrichtt worn.",
        "loginlanguagelabel": "Sproch: $1",
+       "pt-login": "Eilogga",
        "changepassword": "Posswort ändern",
        "oldpassword": "Oids Posswort:",
        "newpassword": "Neichs Posswort:",
        "post-expand-template-argument-warning": "'''Obocht:''' De Seitn enthoit mindastns oa Argument in da Vorlog, wo expandiat z grouss is. \nDe Parameta wean ignoriad.",
        "post-expand-template-argument-category": "Seitn mid ignoriadn Voalognparametan",
        "undo-summary": "Änderrung $1 voh [[Special:Contributions/$2|$2]] ([[User talk:$2|Diskussión]]) ryckgängig gmocht.",
-       "cantcreateaccounttitle": "Benutzerkonto kå ned erstöd wern",
        "viewpagelogs": "Logbiacha fia de Datei ozoagn",
        "currentrev": "Aktuelle Versión",
        "currentrev-asof": "Letzte Version vo $1",
index b3d7e8c..abacb5a 100644 (file)
        "passwordreset-emailtext-user": "Paragamit $1 sa {{SITENAME}} naghahagad nin sarong pagiromdom kan detalye nin saimong panindog para sa {{SITENAME}}\n($4). An minasunod na paragamit {{PLURAL:$3|panindog iyo an|mga panindog iyo an}} na asosyado kaining e-koreong address:\n\n$2\n\n\n{{PLURAL:$3|Ining temporaryong sekretong panlaog|Ining mga temporaryong panlaog}} mapapaso sa {{PLURAL:$5|sarong aldaw|$5 mga aldaw}}.\nIka dapat na maglaog asin magpili nin sarong bagong sekretong panlaog ngunyan. Kun ibang tawo an naghimo kaining kahagadan, o kun saimo nang nagiromdoman an saimong orihinal na sekretong panlaog, asin habo mo nang ribayan ini, ipasapara mo na sana an mensaheng ini asin ipadagos mo nang gamiton an saimong lumang sekretong panlaog.",
        "passwordreset-emailelement": "Paragamit-ngaran: \n$1\n\nTemporaryong sekretong panlaog: \n$2",
        "passwordreset-emailsentemail": "Sarong e-surat sa pagliliwat kan sekretong panlaog an ipinadara na.",
-       "passwordreset-emailsent-capture": "Sarong e-surat sa pagliliwat kan sekretong panlaog an ipinadara na, yaon ipinapahiling sa ibaba.",
-       "passwordreset-emailerror-capture": "Sarong e-surat sa pagliliwat kan sekretong panlaog an pinagpuyos na, yaon ipinapahiling sa ibaba, alagad sa pagpapadara kaini sa {{GENDER:$2|paragamit}} nagpalya: $1",
        "changeemail": "Ribayan an e-koreong address",
        "changeemail-header": "Ribayan an panindog na e-koreong address",
        "changeemail-no-info": "Ika dapat nakalaog na tanganing direktang makagamit kaining pahina.",
        "undo-norev": "An pagliwat dae tabi magigibo nin huli ta ini bakong eksistido o pinagpura na.",
        "undo-summary": "Dae idagos an rebisyon $1 sa [[Special:Contributions/$2|$2]] ([[User talk:$2|olay]])",
        "undo-summary-username-hidden": "Dae idagos an rebisyon sa $1 nin sarong nakatago na paragamit",
-       "cantcreateaccounttitle": "Dai makagibo nin account",
        "cantcreateaccount-text": "An pagbukas nin account halì sa IP na ('''$1''') binágat ni [[User:$3|$3]].\n\n''$2'' an rason na pigtao ni $3",
        "viewpagelogs": "\nHilingon an mga katalaanan para sa pahinang ini",
        "nohistory": "Mayong paghirá nin uusipón sa pahinang ini.",
index fd87b0f..e5a0f8d 100644 (file)
        "passwordreset-emailelement": "Імя ўдзельніка: \n$1\n\nЧасовы пароль: \n$2",
        "passwordreset-emailsentemail": "Калі гэты адрас электроннай пошты далучаны да вашага рахунку, тады будзе дасланы ліст пра скідваньне паролю.",
        "passwordreset-emailsentusername": "Калі ёсьць адрас электроннай пошты, злучаны з гэтым імем удзельніка, тады будзе дасланы ліст пра скідваньне паролю.",
-       "passwordreset-emailsent-capture": "Ліст пра скіданьне паролю быў дасланы, што паказана ніжэй.",
-       "passwordreset-emailerror-capture": "Ліст пра скіданьне паролю быў створаны і паказаны ніжэй, але не ўдалося адправіць яго {{GENDER:$2|ўдзельніку|ўдзельніцы}}: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|Электронны ліст|Электронныя лісты}} скіданьня паролю {{PLURAL:$1|быў дасланы|былі дасланыя}}. {{PLURAL:$1|Імя ўдзельніка і пароль|Сьпіс імёнаў удзельнікаў і паролі}} паказаныя ніжэй.",
        "passwordreset-emailerror-capture2": "Не атрымалася даслаць {{GENDER:$2|удзельніку|удзельніцы}} ліст электроннай поштай: $1 {{PLURAL:$3|Імя ўдзельніка і пароль|Сьпіс імёнаў удзельнікаў і паролі}} паказаныя ніжэй.",
        "passwordreset-nocaller": "Мусіць быць пададзены той, хто робіць выклік",
        "passwordreset-nodata": "Не былі пададзеныя ні імя ўдзельніка, ні адрас электроннай пошты",
        "changeemail": "Зьмяніць або выдаліць адрас электроннай пошты",
        "changeemail-header": "Запоўніце гэтую форму, каб зьмяніць ваш адрас электроннай пошты. Калі вы жадаеце выдаліць адрас электроннай пошты, далучаны да вашага рахунку, пакіньце поле новага адрасу электроннай пошты пустым пры запаўненьні формы.",
-       "changeemail-passwordrequired": "Вам трэба будзе ўвесьці ваш пароль, каб пацьвердзіць гэтую зьмену.",
        "changeemail-no-info": "Для непасрэднага доступу да гэтай старонкі Вам неабходна ўвайсьці ў сыстэму.",
        "changeemail-oldemail": "Цяперашні адрас электроннай пошты:",
        "changeemail-newemail": "Новы адрас электроннай пошты:",
        "undo-nochange": "Выглядае, што праўка ўжо была адмененая.",
        "undo-summary": "Скасаваньне праўкі $1 {{GENDER:$2|удзельніка|удзельніцы}} [[Special:Contributions/$2|$2]] ([[User talk:$2|гутаркі]])",
        "undo-summary-username-hidden": "Вэрсія $1 скасаваная схаваным удзельнікам",
-       "cantcreateaccounttitle": "Немагчыма стварыць рахунак",
        "cantcreateaccount-text": "Стварэньне рахункаў з гэтага IP-адрасу ('''$1''') было заблякаванае [[User:$3|$3]].\n\nПрычына блякаваньня пададзеная $3: ''$2''",
        "cantcreateaccount-range-text": "Стварэньне рахункаў з IP-адрасоў у дыяпазоне <strong>$1</strong>, у які ўваходзіць ваш IP-адрас (<strong>$4</strong>), было забароненае {{GENDER:$3|ўдзельнікам|ўдзельніцай}} [[User:$3|$3]].\n\n{{GENDER:$3|Удзельнікам|Удзельніцай}} $3 была пададзеная наступная прычына: <em>$2</em>.",
        "viewpagelogs": "Паказаць журналы падзеяў для гэтай старонкі",
index fdb5b84..f89f294 100644 (file)
        "passwordreset-emailelement": "Імя ўдзельніка: \n$1\n\nЧасовы пароль: \n$2",
        "passwordreset-emailsentemail": "Калі гэты адрас электроннай пошты злучаны з вашым уліковым запісам, будзе адпраўлены ліст пра скід пароля.",
        "passwordreset-emailsentusername": "Калі ёсць адрас электроннай пошты, злучаны з гэтым імем удзельніка, то будзе дасланы ліст пра скід пароля.",
-       "passwordreset-emailsent-capture": "Ніжэй прыведзены адпраўлены ліст пра скід пароля.",
-       "passwordreset-emailerror-capture": "Ніжэй прыведзены створаны ліст пра скід пароля, яго адпраўка не атрымалася па прычыне: $1",
        "passwordreset-invalideamil": "Няслушны адрас электроннай пошты",
        "passwordreset-nodata": "Не былі пададзены ні імя ўдзельніка, ні адрас электроннай пошты",
        "changeemail": "Змяніць або выдаліць адрас электроннай пошты",
        "changeemail-header": "Запоўніце гэтую форму, каб змяніць свой адрас электроннай пошты. Калі хочаце выдаліць адрас электроннай пошты, злучаны з вашым уліковым запісам, пакіньце поле новага адраса электроннай пошты пустым пры адпраўцы формы.",
-       "changeemail-passwordrequired": "Вам трэба будзе ўвесці свой пароль, каб пацвердзіць гэта змяненне.",
        "changeemail-no-info": "Каб звяртацца непасрэдна да гэтай старонкі, вам варта прадставіцца сістэме.",
        "changeemail-oldemail": "Бягучы адрас электроннай пошты:",
        "changeemail-newemail": "Новы адрас электроннай пошты:",
        "undo-nochange": "Выглядае на тое, што праўка ўжо была адкочаная.",
        "undo-summary": "Адкат версіі $1 аўтарства [[Special:Contributions/$2|$2]] ([[User talk:$2|размова]])",
        "undo-summary-username-hidden": "Адкат версіі $1 схаванага ўдзельніка",
-       "cantcreateaccounttitle": "Немагчыма стварыць рахунак",
        "cantcreateaccount-text": "Стварэнне рахункаў было забаронена для гэтага адрасу IP ('''$1''').\n\nЗабарона зроблена ўдзельнікам [[User:$3|$3]], з такім тлумачэннем: ''$2''",
        "cantcreateaccount-range-text": "Стварэнне ўліковага запісу ўдзельніка з IP-адрасоў у дыяпазоне <strong>$1</strong>, што ўключае ваш адрас IP (<strong>$4</strong>), было забаронена {{GENDER:$3|ўдзельнікам|ўдзельніцай}} [[User:$3|$3]].\n\n$3 {{GENDER:$3|патлумачыў|патлумачыла}} гэта так: <em>$2</em>",
        "viewpagelogs": "Паказаць журналы для гэтай старонкі",
        "special-characters-title-endash": "кароткі працяжнік",
        "special-characters-title-emdash": "доўгі працяжнік",
        "special-characters-title-minus": "мінус",
+       "mw-widgets-dateinput-no-date": "Дата не выбрана",
+       "mw-widgets-titleinput-description-new-page": "старонка яшчэ не існуе",
+       "mw-widgets-titleinput-description-redirect": "перанакіраванне на $1",
        "log-action-filter-all": "Усе",
        "log-action-filter-block-block": "заблакаваць",
        "log-action-filter-block-reblock": "Змена блакіроўкі",
index a5a984b..f7f6f55 100644 (file)
@@ -35,7 +35,8 @@
                        "Miroslav35232",
                        "Ket",
                        "Ricordo.tenerissimo",
-                       "Plamen"
+                       "Plamen",
+                       "Iliev"
                ]
        },
        "tog-underline": "Подчертаване на препратките:",
@@ -77,7 +78,7 @@
        "tog-ccmeonemails": "Получаване на копия на писмата, които пращам на другите потребители",
        "tog-diffonly": "Без показване на съдържанието на страницата при преглед на разлики",
        "tog-showhiddencats": "Показване на скритите категории",
-       "tog-norollbackdiff": "Ð\9fÑ\80опÑ\83Ñ\81кане Ð½Ð° Ñ\80азликоваÑ\82а Ð²Ñ\80Ñ\8aзка Ñ\81лед Ð¸Ð·Ð²Ñ\8aÑ\80Ñ\88ване Ð½Ð° отмяна на редакции",
+       "tog-norollbackdiff": "Ð\9dе Ð¿Ð¾ÐºÐ°Ð·Ð²Ð°Ð¹ Ñ\80азликаÑ\82а Ð¼ÐµÐ¶Ð´Ñ\83 Ñ\80едакÑ\86ииÑ\82е Ñ\81лед отмяна на редакции",
        "tog-useeditwarning": "Предупреждаване при опит за напускане на страница, отворена в режим на редактиране, без да са запазени промените",
        "tog-prefershttps": "Да се използва винаги защитена връзка след влизане",
        "underline-always": "Винаги",
        "protectedinterface": "Тази страница съдържа текст, нужен за работата на системата. Тя е защитена против редактиране, за да се предотвратят възможни злоупотреби.\nЗа извършване на промяна за всички уикита, посетете [https://translatewiki.net/ translatewiki.net], проектът за локализация на MediaWiki.",
        "editinginterface": "<strong>Внимание:</strong> Редактирате страница, която се използва за текстовия интерфейс на софтуера. Промяната й ще повлияе на външния вид на уикито.",
        "translateinterface": "За да добавите или промените преводи за всички уикита, моля, използвайте [https://translatewiki.net/ translatewiki.net], локализиращия проект на МедияУики.",
-       "cascadeprotected": "Тази страница е защитена против редактиране, защото е включена в {{PLURAL:$1|следната страница, която от своя страна има|следните страници, които от своя страна имат}} каскадна защита:\n$2",
+       "cascadeprotected": "Тази страница е защитена против редактиране, защото е включена в {{PLURAL:$1|следната страница, която от своя страна има|следните страници, които от своя страна имат}} „каскадна“ защита:\n$2",
        "namespaceprotected": "Нямате права за редактиране на страници в именно пространство '''$1'''.",
        "customcssprotected": "Нямате права за редактиране на тази CSS страница, защото тя съдържа чужди потребителски настройки.",
        "customjsprotected": "Нямате права за редактиране на тази JavaScript страница, защото тя съдържа чужди потребителски настройки.",
        "password-change-forbidden": "Не можете да променяте пароли в това уики.",
        "externaldberror": "Или е станала грешка в базата от данни при външното удостоверяване, или не ви е позволено да обновявате външната си сметка.",
        "login": "Влизане",
+       "login-security": "Потвърдете идентичността си",
        "nav-login-createaccount": "Регистриране или влизане",
        "userlogin": "Влизане / създаване на сметка",
        "userloginnocreate": "Влизане",
        "createacct-reason-ph": "Защо създавате друга сметка",
        "createacct-submit": "Създаване на сметката",
        "createacct-another-submit": "Създаване на сметка",
+       "createacct-continue-submit": "Продължаване създаването на акаунт",
+       "createacct-another-continue-submit": "Продължаване създаването на акаунт",
        "createacct-benefit-heading": "{{SITENAME}} се създава от хора като вас.",
        "createacct-benefit-body1": "{{PLURAL:$1|редакция|редакции}}",
        "createacct-benefit-body2": "{{PLURAL:$1|страница|страници}}",
        "noname": "Не указахте валидно потребителско име.",
        "loginsuccesstitle": "Успешно влизане",
        "loginsuccess": "'''Влязохте в {{SITENAME}} като „$1“.'''",
-       "nosuchuser": "Ð\9dе Ñ\81Ñ\8aÑ\89еÑ\81Ñ\82вÑ\83ва Ð¿Ð¾Ñ\82Ñ\80ебиÑ\82ел Ñ\81 Ð¸Ð¼Ðµ â\80\9e$1â\80\9c.\nÐ\9fоÑ\82Ñ\80ебиÑ\82елÑ\81киÑ\82е Ð¸Ð¼ÐµÐ½Ð° Ñ\81а Ñ\87Ñ\83вÑ\81Ñ\82виÑ\82елни Ð½Ð° Ð¼Ð°Ð»ÐºÐ¸ Ð¸ Ð³Ð»Ð°Ð²Ð½Ð¸ Ð±Ñ\83кви.\nПроверете изписването или [[Special:CreateAccount|създайте нова сметка]].",
+       "nosuchuser": "Ð\9dе Ñ\81Ñ\8aÑ\89еÑ\81Ñ\82вÑ\83ва Ð¿Ð¾Ñ\82Ñ\80ебиÑ\82ел Ñ\81 Ð¸Ð¼Ðµ â\80\9e$1â\80\9c.\nÐ\9fоÑ\82Ñ\80ебиÑ\82елÑ\81киÑ\82е Ð¸Ð¼ÐµÐ½Ð° Ñ\81а Ñ\87Ñ\83вÑ\81Ñ\82виÑ\82елни ÐºÑ\8aм Ñ\80егиÑ\81Ñ\82Ñ\8aÑ\80а Ð½Ð° Ð±Ñ\83квиÑ\82е.\nПроверете изписването или [[Special:CreateAccount|създайте нова сметка]].",
        "nosuchusershort": "Не съществува потребител с името „$1“. Проверете изписването.",
        "nouserspecified": "Необходимо е да се посочи потребителско име.",
        "login-userblocked": "Този потребител е блокиран. Влизането в системата не е позволено.",
        "resetpass-no-info": "За да достъпвате тази страница директно, необходимо е да влезете в системата.",
        "resetpass-submit-loggedin": "Промяна на паролата",
        "resetpass-submit-cancel": "Отказ",
-       "resetpass-wrong-oldpass": "Невалидна временна или текуща парола.\nВъзможно е вече успешно да сте сменили паролата си или да сте поискали нова временна парола.",
+       "resetpass-wrong-oldpass": "Невалидна временна или текуща парола.\nВъзможно е вече да сте сменили паролата си или да сте поискали нова временна парола.",
        "resetpass-recycled": "Моля, променете паролата си с такава, различна от текущата.",
        "resetpass-temp-emailed": "Вие сте влезли в системата с помощта на временен код, който е изпратен чрез електронна поща.\nЗа да завършите влизането в системата, трябва да въведете нова парола тук:",
        "resetpass-temp-password": "Временна парола:",
        "resetpass-abort-generic": "Промяната на паролата беше прекъсната от използвано разширение.",
        "resetpass-expired": "Срокът на валидност на паролата е изтекъл. Изберете нова парола за влизане.",
        "resetpass-expired-soft": "Вашата парола е изтекла и трябва да бъде променена. Моля, въведете нова парола сега или натиснете бутона \"{{int:authprovider-resetpass-skip-label}}\" за да я промените по-късно.",
-       "resetpass-validity-soft": "Ð\9cолÑ\8f, Ð²Ñ\8aведеÑ\82е Ð½Ð¾Ð²Ð° Ð¿Ð°Ñ\80ола Ñ\81ега Ð¸Ð»Ð¸ Ð½Ð°Ñ\82иÑ\81неÑ\82е Ð±Ñ\83Ñ\82она \"{{int:authprovider-resetpass-skip-label}}\" за да я промените по-късно.",
+       "resetpass-validity-soft": "Ð\92аÑ\88аÑ\82а Ð¿Ð°Ñ\80ола Ðµ Ð½ÐµÐ²Ð°Ð»Ð¸Ð´Ð½Ð°: $1\n\nÐ\9cолÑ\8f, Ð²Ñ\8aведеÑ\82е Ð½Ð¾Ð²Ð° Ð¿Ð°Ñ\80ола Ð¸Ð»Ð¸ Ð½Ð°Ñ\82иÑ\81неÑ\82е Ð±Ñ\83Ñ\82она â\80\9e{{int:authprovider-resetpass-skip-label}}â\80\9c за да я промените по-късно.",
        "passwordreset": "Възстановяване на парола",
        "passwordreset-text-one": "Попълването на формуляра ще доведе до възстановяване на паролата.",
        "passwordreset-text-many": "{{PLURAL:$1|За получаване на временна парола по електронна поща е необходимо да попълните едно от полетата.}}",
        "passwordreset-emailelement": "Потребителско име: \n$1\n\nВременна парола: \n$2",
        "passwordreset-emailsentemail": "Ако електронната Ви поща е свързана със сметката Ви, на нея е изпратено писмо за възстановяване на паролата.",
        "passwordreset-emailsentusername": "Ако това потребителско име е свързано с електронна поща, е изпратено писмо за възстановяване на паролата.",
-       "passwordreset-emailsent-capture": "По-долу е показано електронното писмо за възстановяване на паролата, което беше изпратено.",
-       "passwordreset-emailerror-capture": "По-долу е показано създадено електронно писмо за възстановяване на паролата, което не беше изпратено на {{GENDER:$2|потребителя}}: $1",
        "passwordreset-invalideamil": "Неправилен email адрес",
        "changeemail": "Промяна или премахване на адреса за е-поща",
        "changeemail-header": "Промяна на адреса за е-поща на сметката",
-       "changeemail-passwordrequired": "Трябва да въведете паролата си, за да потвърдите тази промяна.",
        "changeemail-no-info": "За да достъпвате тази страница директно, необходимо е да влезете в системата.",
        "changeemail-oldemail": "Текущ адрес за е-поща:",
        "changeemail-newemail": "Нов адрес за е-поща:",
        "minoredit": "Това е малка промяна",
        "watchthis": "Наблюдаване на страницата",
        "savearticle": "Съхраняване",
+       "savechanges": "Съхраняване на промените",
        "publishpage": "Публикуване на страницата",
+       "publishchanges": "Публикуване на промените",
        "preview": "Предварителен преглед",
        "showpreview": "Предварителен преглед",
        "showdiff": "Показване на промените",
        "accmailtext": "Случайно генерирана парола за [[User talk:$1|$1]] беше изпратена на $2. Паролата може да бъде променена от страницата ''[[Special:ChangePassword|„Промяна на паролата“]]'' след влизане в системата.",
        "newarticle": "(нова)",
        "newarticletext": "Последвахте препратка към страница, която все още не съществува.\nЗа да я създадете, просто започнете да пишете в долната текстова кутия\n(вижте [$1 помощната страница] за повече информация).",
-       "anontalkpagetext": "----''Това е дискусионната страница на анонимен потребител, който все още няма регистрирана сметка или не я използва, затова се налага да използваме IP-адрес, за да го идентифицираме. Такъв адрес може да се споделя от няколко потребители.''\n\n''Ако сте анонимен потребител и мислите, че тези неуместни коментари са отправени към вас, [[Special:CreateAccount|регистрирайте се]] или [[Special:UserLogin|влезте в системата]], за да избегнете евентуално бъдещо объркване с други анонимни потребители.''",
+       "anontalkpagetext": "----\n<em>Това е дискусионната страница на анонимен потребител, който все още няма регистрирана сметка или не я използва</em>\nЗатова се налага да използваме IP-адрес, за да го идентифицираме.\nТакъв адрес може да се споделя от няколко потребители.\nАко сте анонимен потребител и мислите, че тези неуместни коментари са отправени към вас, [[Special:CreateAccount|регистрирайте се]] или [[Special:UserLogin|влезте в системата]], за да избегнете евентуално бъдещо объркване с други анонимни потребители.",
        "noarticletext": "Понастоящем няма текст на тази страница. Можете да [[Special:Search/{{PAGENAME}}|потърсите за заглавието на страницата]] в други страници, да <span class=\"plainlinks\">[{{fullurl:{{#Special:Log}}|page={{FULLPAGENAMEE}}}} потърсите в съответните дневници] или [{{fullurl:{{FULLPAGENAME}}|action=edit}} да я създадете]</span>.",
        "noarticletext-nopermission": "Текущо в тази страница няма текст.\nМожете да [[Special:Search/{{PAGENAME}}|потърсите заглавието на тази страница ]] в други страници или да <span class=\"plainlinks\">[{{fullurl:{{#Special:Log}}|page={{FULLPAGENAMEE}}}} потърсите в съответните дневници]</span>, но нямате права да създадете тази страница.",
        "missing-revision": "Версия #$1 на страницата „{{FULLPAGENAME}}“ не съществува.\n\nТова обикновено се дължи на препратка от историята на страницата, която е била изтрита.\nПодробности могат да бъдат открити в [{{fullurl:{{#Special:Log}}/delete|page={{FULLPAGENAMEE}}}} дневника на изтриванията].",
        "userpage-userdoesnotexist": "Няма регистрирана потребителска сметка за „<nowiki>$1</nowiki>“. Изисква се потвърждение, че желаете да създадете/редактирате тази страница?",
        "userpage-userdoesnotexist-view": "Не е регистрирана потребителска сметка на име „$1“.",
        "blocked-notice-logextract": "В момента този потребител е блокиран.\nПо-долу за справка е показан последният запис от Дневника на блокиранията:",
-       "clearyourcache": "'''Забележка:''' За да се видят промените, необходимо е след съхраняване на страницата, кешът на браузъра да бъде изтрит.\n* '''Firefox / Safari:''' Задържа се клавиш ''Shift'' и се щраква върху ''Презареждане'' (''Reload'') или чрез клавишната комбинация ''Ctrl-Shift-R'' (''⌘-Shift-R'' за Mac);\n* '''Google Chrome:''' клавишна комбинация ''Ctrl-Shift-R'' (''⌘-Shift-R'' за Mac)\n* '''Internet Explorer:''' Задържа се клавиш ''Ctrl'' и се щраква върху ''Refresh'' или чрез клавишната комбинация ''CTRL-F5'';\n* '''Opera:''' кешът се изчиства през менюто ''Tools → Preferences''.",
+       "clearyourcache": "<strong>Забележка:</strong> За да се видят промените, необходимо е след съхраняване на страницата, кешът на браузъра да бъде изтрит.\n* <strong>Firefox / Safari:</strong> Задържа се клавиш <em>Shift</em> и се щраква върху <em>Презареждане</em> (<em>Reload</em>) или чрез клавишната комбинация <em>Ctrl-F5</em> or <em>Ctrl-R</em> (<em>⌘-R</em> за Mac);\n* <strong>Google Chrome:</strong> клавишна комбинация <em>Ctrl-Shift-R</em> (<em>⌘-Shift-R</em> за Mac)\n* <strong>Internet Explorer:</strong> Задържа се клавиш <em>Ctrl</em> и се щраква върху <em>Refresh</em> или чрез клавишната комбинация <em>Ctrl-F5</em>;\n* <strong>Opera:</strong> кешът се изчиства през менюто <em>Tools → Settings</em> (<em>Opera → Preferences</em> за Mac) след което <em>Privacy & security → Clear browsing data → Cached images and files</em>.",
        "usercssyoucanpreview": "'''Съвет:''' Използвайте бутона „{{int:showpreview}}“, за да изпробвате новия код на CSS преди съхранението.",
        "userjsyoucanpreview": "'''Съвет:''' Използвайте бутона „{{int:showpreview}}“, за да изпробвате новия код на Джаваскрипт преди съхранението.",
        "usercsspreview": "'''Не забравяйте, че това е само предварителен преглед на кода на CSS. Страницата все още не е съхранена!'''",
        "undo-failure": "Редакцията не може да бъде върната поради конфликтни междинни редакции.",
        "undo-norev": "Редакцията не може да бъде върната, тъй като не съществува или е била изтрита.",
        "undo-summary": "Премахната редакция $1 на [[Special:Contributions/$2|$2]] ([[User talk:$2|беседа]])",
-       "cantcreateaccounttitle": "Невъзможно е да бъде създадена потребителска сметка.",
        "cantcreateaccount-text": "[[User:$3|Потребител:$3]] е блокирал(а) създаването на сметки от този IP-адрес ('''$1''').\n\nПричината, изложена от $3, е ''$2''",
        "viewpagelogs": "Преглед на извършените административни действия по страницата",
        "nohistory": "Няма редакционна история за тази страница.",
        "revdelete-submit": "Прилагане към {{PLURAL:$1|избраната версия|избраните версии}}",
        "revdelete-success": "'''Видимостта на версията беше променена успешно.'''",
        "revdelete-failure": "'''Видимостта на редакцията не може да бъде обновена:'''\n$1",
-       "logdelete-success": "Видимостта на събитието беше променена.",
+       "logdelete-success": "Видимостта на дневника е установена.",
        "logdelete-failure": "'''Видимостта на дневника не може да бъде променяна:'''\n$1",
        "revdel-restore": "промяна на видимостта",
        "pagehist": "История на страницата",
        "grouppage-sysop": "{{ns:project}}:Администратори",
        "grouppage-bureaucrat": "{{ns:project}}:Бюрократи",
        "grouppage-suppress": "{{ns:project}}:Ревизори",
-       "right-read": "четене на страници",
+       "right-read": "Четене на страници",
        "right-edit": "редактиране на страници",
        "right-createpage": "Създаване на страници (които не са беседи)",
        "right-createtalk": "Създаване на дискусионни страници",
        "right-move-rootuserpages": "Преместване на основни потребителски страници",
        "right-move-categorypages": "Преместване на категорийни страници",
        "right-movefile": "Преместване на файлове",
-       "right-suppressredirect": "без създаване на пренасочване от старото име при преместване на страница",
+       "right-suppressredirect": "Ð\91ез създаване на пренасочване от старото име при преместване на страница",
        "right-upload": "Качване на файлове",
        "right-reupload": "Презаписване на съществуващ файл",
        "right-reupload-own": "Презаписване на съществуващ файл, качен от същия потребител",
        "right-reupload-shared": "Предефиниране на едноименните файлове от общото мултимедийно хранилище с локални",
        "right-upload_by_url": "качване на файл от URL адрес",
        "right-purge": "изчистване на складираното съдържание на страниците без показване на страница за потвърждение",
-       "right-autoconfirmed": "редактиране на полузащитени страници",
-       "right-bot": "третиране като автоматизиран процес",
+       "right-autoconfirmed": "Редактиране на полузащитени страници",
+       "right-bot": "Третиране като автоматизиран процес",
        "right-nominornewtalk": "Малките промени по дискусионните страници не предизвикват известието за ново съобщение",
-       "right-apihighlimits": "използване на крайните предели в API заявките",
+       "right-apihighlimits": "Ð\98зползване на крайните предели в API заявките",
        "right-writeapi": "Употреба на API за писане",
-       "right-delete": "изтриване на страници",
+       "right-delete": "Ð\98зтриване на страници",
        "right-bigdelete": "изтриване на страници с големи редакционни истории",
-       "right-deleterevision": "изтриване и възстановяване на отделни версии на страниците",
+       "right-deletelogentry": "Изтриване и възстановяване на отделни записи в дневника",
+       "right-deleterevision": "Изтриване и възстановяване на отделни версии на страниците",
        "right-deletedhistory": "преглеждане на записи от изтрити редакционни истории без асоциирания към тях текст",
        "right-deletedtext": "Преглед на изтрития текст и промените между изтритите версии",
        "right-browsearchive": "търсене на изтрити страници",
-       "right-undelete": "възстановяване на страници",
-       "right-suppressrevision": "преглед и възстановяване на версии, скрити от администраторите",
+       "right-undelete": "Ð\92ъзстановяване на страници",
+       "right-suppressrevision": "Ð\9fреглед и възстановяване на версии, скрити от администраторите",
        "right-viewsuppressed": "Преглеждане на версии, скрити от който и да е потребител",
-       "right-suppressionlog": "преглеждане на тайните дневници",
+       "right-suppressionlog": "Ð\9fреглеждане на тайните дневници",
        "right-block": "спиране на достъпа до редактиране",
-       "right-blockemail": "блокиране на потребители да изпращат писма по е-поща",
+       "right-blockemail": "Ð\91локиране на потребители да изпращат писма по е-поща",
        "right-hideuser": "блокиране и скриване на потребителско име",
        "right-ipblock-exempt": "пренебрегване на блокирания по IP blocks, автоматични блокирания и блокирани IP интервали",
        "right-unblockself": "Собствено отблокиране",
        "right-protect": "променяне на нивото на защита и редактиране на защитени страници",
        "right-editprotected": "редактиране на защитени страници (без каскадна защита)",
-       "right-editinterface": "редактиране на потребителския интерфейс",
+       "right-editinterface": "Редактиране на потребителския интерфейс",
        "right-editusercssjs": "редактиране на CSS и JS файловете на други потребители",
        "right-editusercss": "редактиране на CSS файловете на други потребители",
        "right-edituserjs": "редактиране на JS файловете на други потребители",
        "right-import": "внасяне на страници от други уикита",
        "right-importupload": "внасяне на страници от качен файл",
        "right-patrol": "отбелязване на редакциите като проверени",
-       "right-autopatrol": "автоматично отбелязване на редакции като проверени",
+       "right-autopatrol": "Ð\90втоматично отбелязване на редакции като проверени",
        "right-patrolmarks": "Показване на отбелязаните като патрулирани последни промени",
        "right-unwatchedpages": "преглеждане на списъка с ненаблюдаваните страници",
        "right-mergehistory": "сливане на редакционни истории на страници",
        "action-viewmywatchlist": "преглед на списъка ви за наблюдение",
        "action-viewmyprivateinfo": "преглеждане на личните данни",
        "action-editmyprivateinfo": "редактиране на личната си информация",
+       "action-purge": "почисти кеша на тази страница",
        "nchanges": "$1 {{PLURAL:$1|промяна|промени}}",
        "enhancedrc-since-last-visit": "$1 {{PLURAL:$1|от последното посещение}}",
        "enhancedrc-history": "история",
        "apihelp-no-such-module": "Модул \"$1\" не беше намерен.",
        "apisandbox-fullscreen": "Разшири полето",
        "apisandbox-reset": "Изчистване",
-       "apisandbox-examples": "Пример",
+       "apisandbox-examples": "Примери",
        "apisandbox-dynamic-parameters-add-placeholder": "Име на параметъра",
        "apisandbox-results": "Резултати",
        "booksources": "Източници на книги",
        "activeusers-hidesysops": "Скриване на администраторите",
        "activeusers-noresult": "Няма намерени потребители.",
        "listgrouprights": "Права по потребителски групи",
-       "listgrouprights-summary": "По-долу на тази страница е показан списък на групите потребители в това уики с асоциираните им права за достъп. Допълнителна информация за отделните права може да бъде намерена [[{{MediaWiki:Listgrouprights-helppage}}|тук]].",
+       "listgrouprights-summary": "По-долу на тази страница е показан списък на групите потребители в това уики и права им за достъп. Допълнителна информация за отделните права може да бъде намерена [[{{MediaWiki:Listgrouprights-helppage}}|тук]].",
        "listgrouprights-key": "Легенда:\n* <span class=\"listgrouprights-granted\">Поверено право</span>\n* <span class=\"listgrouprights-revoked\">Отнето право</span>",
        "listgrouprights-group": "Група",
        "listgrouprights-rights": "Права",
        "sessionfailure": "Изглежда има проблем със сесията ви; действието беше отказано като предпазна мярка срещу крадене на сесията. Натиснете бутона за връщане на браузъра, презаредете страницата, от която сте дошли, и опитайте отново.",
        "changecontentmodel-title-label": "Заглавие на страницата",
        "changecontentmodel-reason-label": "Причина:",
+       "changecontentmodel-success-text": "Типът на съдържанието на [[:$1]] е успешно променен.",
        "protectlogpage": "Дневник на защитата",
        "protectlogtext": "Списък на промените в защитата за страницата.\nМожете да прегледате и [[Special:ProtectedPages|списъка на текущо защитените страници]].",
        "protectedarticle": "защити „[[$1]]“",
        "movenosubpage": "Тази страница няма подстраници.",
        "movereason": "Причина:",
        "revertmove": "връщане",
-       "delete_and_move_text": "== Наложително изтриване ==\n\nЦелевата страница „[[:$1]]“ вече съществува. Искате ли да я изтриете, за да освободите място за преместването?",
+       "delete_and_move_text": "Целевата страница „[[:$1]]“ вече съществува.\nИскате ли да я изтриете, за да освободите място за преместването?",
        "delete_and_move_confirm": "Да, искам да изтрия тази страница.",
        "delete_and_move_reason": "Изтрита, за да се освободи място за преместване от „[[$1]]“",
        "selfmove": "Страницата не може да бъде преместена, тъй като целевото име съвпада с първоначалното ѝ заглавие.",
        "patrol-log-page": "Дневник на патрула",
        "patrol-log-header": "Тази страница съдържа дневник на проверените версии.",
        "log-show-hide-patrol": "$1 на Дневника на патрула",
+       "log-show-hide-tag": "$1 на дневника на отбелязванията",
        "deletedrevision": "Изтрита стара версия $1",
        "filedeleteerror-short": "Грешка при изтриване на файл: $1",
        "filedeleteerror-long": "Възникнаха грешки при изтриването на файла:\n\n$1",
        "exif-dc-contributor": "Сътрудници",
        "exif-dc-date": "Дата(и)",
        "exif-dc-rights": "Права",
+       "exif-dc-type": "Вид медия",
        "exif-isospeedratings-overflow": "По-голяма от 65535",
        "exif-iimcategory-ace": "Изкуствa, култура и забавление",
        "exif-iimcategory-clj": "Престъпност и право",
        "scarytranscludefailed": "[Зареждането на шаблона за $1 не сполучи]",
        "scarytranscludetoolong": "[Адресът е твърде дълъг]",
        "deletedwhileediting": "'''Внимание''': Страницата е била изтрита, след като сте започнали да я редактирате!",
-       "confirmrecreate": "Потребителят [[User:$1|$1]] ([[User talk:$1|беседа]]) е изтрил страницата, откакто сте започнали да я редактирате, като е посочил следното обяснение:\n: ''$2''\nПотвърдете, че наистина желаете да създадете страницата отново.",
-       "confirmrecreate-noreason": "Потребител [[User:$1|$1]] ([[User talk:$1|беседа]]) изтри тази страница след като сте започнали да я редактирате.  Необходимо е потвърждение, че наистина желаете да създадете страницата отново.",
+       "confirmrecreate": "Потребител [[Потребител:$1|$1]] ([[Потребител беседа:$1|беседа]]) е {{GENDER:$1|изтрил}} страницата, откакто сте започнали да я редактирате, като е посочил следното обяснение:\n: <em>$2</em>\nПотвърдете, че наистина желаете да създадете страницата отново.",
+       "confirmrecreate-noreason": "Потребител [[User:$1|$1]] ([[User talk:$1|беседа]]) {{GENDER:$1|изтри}} тази страница след като сте започнали да я редактирате. Необходимо е потвърждение, че наистина желаете да създадете страницата отново.",
        "recreate": "Ново създаване",
        "confirm_purge_button": "Добре",
        "confirm-purge-top": "Изчистване на складираното копие на страницата?",
        "watchlistedit-raw-added": "{{PLURAL:$1|1 страница беше добавена|$1 страници бяха добавени}}:",
        "watchlistedit-raw-removed": "{{PLURAL:$1|Една страница беше премахната|$1 страници бяха премахнати}}:",
        "watchlistedit-clear-legend": "Изчистване на списъка за наблюдение",
+       "watchlistedit-clear-explain": "Всички заглавия ще бъдат премахнати от списъка ви за наблюдение",
        "watchlistedit-clear-titles": "Заглавия:",
        "watchlistedit-clear-submit": "Изчистване на списъка за наблюдение (Необратимо!)",
        "watchlistedit-clear-done": "Списъкът за наблюдение беше изчистен.",
        "revdelete-uname-hid": "скрито потребителско име",
        "revdelete-restricted": "добавени ограничения за администраторите",
        "revdelete-unrestricted": "премахнати ограничения за администраторите",
-       "logentry-block-block": "$1 блокира {{GENDER:$4|$3}} със срок на изтичане $5 $6",
-       "logentry-block-reblock": "$1 промени настройките на блокиране на {{GENDER:$4|$3}} със срок на изтичане $5 $6",
+       "logentry-block-block": "$1 {{GENDER:$2|блокира }} {{GENDER:$4|$3}} със срок на изтичане $5 $6",
+       "logentry-block-reblock": "$1 {{GENDER:$2|промени }} настройките на блокиране на {{GENDER:$4|$3}} със срок на изтичане $5 $6",
        "logentry-suppress-block": "$1 {{GENDER:$2|блокира}} {{GENDER:$4|$3}} със срок на изтичане $5 $6",
        "logentry-suppress-reblock": "$1 {{GENDER:$2|промени}} настройките на блокиране на {{GENDER:$4|$3}} със срок на изтичане $5 $6",
        "logentry-move-move": "$1 {{GENDER:$2|премести}} страница „$3“ като „$4“",
        "logentry-newusers-create2": "$1 {{GENDER:$2|създаде}} потребителска сметка $3",
        "logentry-newusers-byemail": "$1 {{GENDER:$2|създаде}} потребителската сметка $3, като паролата за нея беше изпратена по е-поща",
        "logentry-newusers-autocreate": "Сметката $1 беше {{GENDER:$2|създадена}} автоматично",
-       "logentry-rights-rights": "$1 {{GENDER:$2|промени}} потребителската група на $3 от $4 на $5",
+       "logentry-rights-rights": "$1 {{GENDER:$2|промени}} потребителската група на {{GENDER:$6|$3}} от $4 на $5",
        "logentry-rights-rights-legacy": "$1 {{GENDER:$2|промени}} потребителската група на $3",
        "logentry-rights-autopromote": "$1 е автоматично {{GENDER:$2|повишен|повишена}} от $4 до $5",
        "logentry-upload-upload": "$1 {{GENDER:$2|качи}} $3",
        "api-error-badaccess-groups": "Нямате необходимите права, за да качвате файлове в това уики.",
        "api-error-badtoken": "Вътрешна грешка: неправилен маркер.",
        "api-error-copyuploaddisabled": "Качването през URL е забранено на този сървър.",
-       "api-error-duplicate": "На сайта вече има качени {{PLURAL:$1|друг файл|други файла}} с идентично съдържание.",
+       "api-error-duplicate": "На сайта вече има {{PLURAL:$1|качен друг файл|качени други файлове}} с идентично съдържание.",
        "api-error-duplicate-archive": "На сайта вече е имало {{PLURAL:$1|качен друг файл|качени други файла}} с идентично съдържание, {{PLURAL:$1|който е бил изтрит|които са били изтрити}}.",
        "api-error-empty-file": "Заявеният за качване файл беше празен.",
        "api-error-emptypage": "Създаването на нови, празени страници, не е разрешено.",
        "mw-widgets-dateinput-placeholder-month": "ГГГГ-ММ",
        "mw-widgets-titleinput-description-new-page": "страницата все още не съществува",
        "mw-widgets-titleinput-description-redirect": "пренасочване към $1",
-       "randomrootpage": "Случайна начална страница",
+       "randomrootpage": "Случайна основна страница",
+       "log-action-filter-block": "Вид на блокирането:",
+       "log-action-filter-delete": "Вид на изтриването:",
+       "log-action-filter-newusers": "Вид на създаването на акаунт:",
        "log-action-filter-protect": "Тип защита:",
+       "log-action-filter-rights": "Вид на промяната на правата за достъп:",
        "log-action-filter-upload": "Тип качване:",
        "log-action-filter-all": "Всички",
        "log-action-filter-block-block": "Блокиране",
index 6f85ebb..5b12678 100644 (file)
        "passwordreset-emailtext-user": "{{SITENAME}} ($4) पर सदस्य $1 राउर {{PLURAL:$3|खाता}} के गुप्तशब्द के पुनर्स्थापित करे के अनुरोध कइले बानी। इ ई-मेल पता से निम्न {{PLURAL:$3|खाता जुड़ल बा}}:\n\n$2\n\n{{PLURAL:$3|इ}} अस्थायी गुप्तशब्द {{PLURAL:$5|एक दिन|$5 दिन}} के बाद काम ना करी।\nरउआ खाता में प्रवेश करके एगो नया गुप्तशब्द अभीये चुन लेवे के चाहीं। यदि इ अनुरोध केहु अउर कइले बा, या फिर रउआ आपन मूल गुप्तशब्द याद आ गईल बा, अउर रउआ {{PLURAL:$3|आपन}} गुप्तशब्द नईखीं बदले के चाहत त, रउआ इ संदेश के अनदेखा कर के आपन पुरनका गुप्तशब्द के प्रयोग जारी रख सकत बानीं।",
        "passwordreset-emailelement": "सदस्यनाम: \n$1\n\nअस्थायी गुप्तशब्द: \n$2",
        "passwordreset-emailsentemail": "एगो गुप्तशब्द रिसेट ई-मेल भेजल जा चुकल बा।",
-       "passwordreset-emailsent-capture": "नीचे दिखावल गईल गुप्तशब्द पुनर्स्थापना ई-मेल भेज दिहल गईल बा।",
-       "passwordreset-emailerror-capture": "नीचे दिखावल गईल गुप्तशब्द पुनर्स्थापना ई-मेल उत्पन्न करल गईल रहल, परंतु उ के {{GENDER:$2|सदस्य}} के भेजे के क्रिया असफल रहल।\nत्रुटि: $1",
        "changeemail": "ई-मेल पता बदलीं",
        "changeemail-header": "खाता के ई-मेल पता बदलीं",
        "changeemail-no-info": "इ पन्ना के सिधे प्रयोग करे खातिर रउआ पहिले खाता में प्रवेश करे के पड़ी।",
        "newarticle": "(नया)",
        "newarticletext": "रउआ एगो अइसन कड़ी के पन्ना के अनुसरण कइले बानी जवन अभी तक उपलब्ध नइखे।\nपन्ना बनावे खातिर, नीचे के बाकस में टाइप करे के शुरु करीं (ज्यादा जानकारी खातिर देखीं [$1 मदद पन्ना])।\nयदि रउआ अहिजा गलती से आ गइल बानी त, आपन ब्राउजर के '''बैक''' (Back) बटन दबाईं!",
        "anontalkpagetext": "----''इ वार्ता पन्ना उन अनाम सदस्यन खातिर बा जिन्हन के या त खाता नइखे खोलल गइल या खाता के प्रयोग नइखन करत।\nएहि खातिर उन्हन के पहिचान खातिर हमनी के उनकर आइ॰पी पता के प्रयोग करे के पड़ेला।\nआइ॰पी पता कई सदस्यन खातिर साझा हो सकत बा।\nयदि आप एगो अनाम सदस्य बानी अउर आपके लागत बा कि आपके बारे में अप्रासंगिक टीका टिप्पणी करल गइल बा त कृपया [[Special:CreateAccount|सदस्यता लिहीं]] या [[Special:UserLogin|सत्रारंभ करीं]] ताकि अन्य अनाम सदस्यन में से आपके अलग से पहिचानल जा सके।''",
-       "noarticletext": "à¤\8f à¤ªà¤¨à¥\8dना à¤®à¥\87 à¤\85भà¥\80 à¤²à¥\87 à¤\95à¥\8cनà¥\8bà¤\82 à¤¸à¤¾à¤®à¤\97à¥\8dरà¥\80 à¤¨à¤\87à¤\96à¥\87। \nरà¤\89à¤\86 à¤¦à¥\81सरा à¤ªà¤¨à¥\8dना à¤®à¥\87à¤\82 [[Special:Search/{{PAGENAME}}|à¤\8f à¤\9fाà¤\87à¤\9fिल à¤\95à¥\87 à¤\96à¥\8bà¤\9c]] à¤\95र à¤¸à¤\95त à¤¬à¤¾à¤¨à¥\80à¤\82।",
+       "noarticletext": "à¤\8f à¤ªà¤¨à¥\8dना à¤®à¥\87 à¤\85भà¥\80 à¤\95à¥\8cनà¥\8bà¤\82 à¤¸à¤¾à¤®à¤\97à¥\8dरà¥\80 à¤¨à¤\87à¤\96à¥\87।\nरà¤\89à¤\86à¤\81 à¤¦à¥\81सरा à¤ªà¤¨à¥\8dना à¤®à¥\87à¤\82 [[Special:Search/{{PAGENAME}}|à¤\8f à¤\9fाà¤\87à¤\9fिल à¤\95à¥\87 à¤\96à¥\8bà¤\9c]] à¤\95र à¤¸à¤\95त à¤¬à¤¾à¤¨à¥\80à¤\82,\nया <span class=\"plainlinks\">[{{fullurl:{{#Special:Log}}|page={{FULLPAGENAMEE}}}} à¤¯à¤¾ à¤¸à¤\82बà¤\82धित à¤²à¥\89à¤\97 à¤\96à¥\8bà¤\9c à¤¸à¤\95त à¤¬à¤¾à¤¨à¥\80]</span>, à¤¬à¤¾à¤\95à¥\80 à¤°à¤\89à¤\86 à¤\95à¥\87 à¤\88 à¤ªà¤¨à¥\8dना à¤¬à¤¨à¤¾à¤µà¥\87 à¤\95à¥\87 à¤ªà¤°à¤®à¥\80शन à¤¨à¤\87à¤\96à¥\87।",
        "noarticletext-nopermission": "ए पन्ना मे अभी कौनों सामग्री नइखे।\nरउआँ दुसरा पन्ना में [[Special:Search/{{PAGENAME}}|ए टाइटिल के खोज]] कर सकत बानीं,\nया <span class=\"plainlinks\">[{{fullurl:{{#Special:Log}}|page={{FULLPAGENAMEE}}}} या संबंधित लॉग खोज सकत बानी]</span>, बाकी रउआ के ई पन्ना बनावे के परमीशन नइखे।",
        "missing-revision": "\"{{FULLPAGENAME}}\" पन्ना के संशोधन #$1 उपलब्ध नइखे।\n\nसाधारण रुप से इ एगो हटावल गइल पन्ना के पुरान लिंक पर क्लिक कइला से होखेला।\nअधिक जानकारी खातिर आप [{{fullurl:{{#Special:Log}}/delete|page={{FULLPAGENAMEE}}}} हटावे के लॉग] देख सकत बानी।",
        "userpage-userdoesnotexist": "सदस्य खाता \"$1\" पंजीकृत नइखे।\nकृपया जाँच लीं कि आप इ पन्ना संपादित अथवा निर्मित करे के चाहत बानी कि ना।",
        "undo-nochange": "लागत बा की ई संपादन पहिलहीं वापस लिहल जा चुकल बाटे।",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|वार्ता]]) के द्वारा कइल $1 बदलाव के वापस कइल गइल",
        "undo-summary-username-hidden": "एगो छिपल सदस्य द्वारा कइल बदलाव $1 वापस कइल गइल",
-       "cantcreateaccounttitle": "खाता खुल नईखे सकत",
        "cantcreateaccount-text": "एह आइपी पता (IP address)(<strong>$1</strong>) द्वारा नया खाता बनावे पर  [[User:$3|$3]] द्वारा रोक लगावल गइल बा।\n\nएकरा खातिर $3 के दिहल कारण:<em>$2</em>",
        "cantcreateaccount-range-text": "आइपी पता बिस्तार (IP address range) <strong>$1</strong> पर, जेवना में आपके आइपी (<strong>$4</strong>) भी बा, नया खाता बनावे पर [[User:$3|$3]] द्वारा रोक लगावल गइल बा।\n\nएकरा खातिर $3 के दिहल कारण बा:<em>$2</em>",
        "viewpagelogs": "ए पन्ना खातिर लॉग कुल देखीं",
        "revisionasof": "$1 ले भइल नया बदलाव",
        "revision-info": "{{GENDER:$6|$2}}$7 के द्वारा $1 के संशोधन",
        "previousrevision": "← पुरान संशोधन",
-       "nextrevision": "नया à¤¸à¤\82à¤ोधन →",
-       "currentrevisionlink": "हाल à¤\95à¥\87 à¤¸à¤\82à¤ोधन",
+       "nextrevision": "नया à¤¸à¤\82सोधन →",
+       "currentrevisionlink": "हाल à¤\95à¥\87 à¤¸à¤\82सोधन",
        "cur": "हाल",
        "next": "अगिला",
        "last": "पछिला",
        "contributions": "{{GENDER:$1|सदस्य}} योगदान",
        "contributions-title": " $1 खातिर प्रयोगकर्ता योगदान",
        "mycontris": "हमार योगदान",
+       "anoncontribs": "योगदान",
        "nocontribs": "ई मानदंड से मिलत जुलत कौनो बदलाव ना मिलल।",
        "uctop": "(हाल के)",
        "month": "महीना से (आ ओ से पहिले):",
        "whatlinkshere-next": "{{PLURAL:$1|अगिला|अगिला $1}}",
        "whatlinkshere-links": "← कड़ी",
        "whatlinkshere-hideredirs": "$1 अनुप्रेषण",
-       "whatlinkshere-hidetrans": "$1 à¤\9fà¥\8dरानà¥\8dसà¥\8dà¤\95à¥\8dलà¥\8dयà¥\81à¤\9cनà¥\8dस",
+       "whatlinkshere-hidetrans": "$1 à¤\9fà¥\8dराà¤\82सà¤\95à¥\8dलà¥\82à¤\9cन",
        "whatlinkshere-hidelinks": "$1 कड़ी",
        "whatlinkshere-hideimages": "$1 फ़ाइल लिंक",
        "whatlinkshere-filters": "छननी",
        "importbadinterwiki": "खराब इंटरविकि कड़ी",
        "importsuccess": "आयात पूरा भइल!",
        "import-logentry-upload-detail": "$1 {{PLURAL:$1|संशोधन|संशोधनसभ}} लावल गइल",
-       "tooltip-pt-userpage": "हमार सदस्य पन्ना",
-       "tooltip-pt-mytalk": "हमार बातचीत पन्ना",
-       "tooltip-pt-preferences": "हमार सेटिंग",
+       "tooltip-pt-userpage": "{{GENDER:|राउर सदस्य}} पन्ना",
+       "tooltip-pt-mytalk": "{{GENDER:|राउर}} बातचीत पन्ना",
+       "tooltip-pt-preferences": "{{GENDER:|राउर}} पसंद",
        "tooltip-pt-watchlist": "राउर धियानसूची में पन्ना सब के लिस्ट",
-       "tooltip-pt-mycontris": "राउर सब योगदान के लिस्ट",
+       "tooltip-pt-mycontris": "{{GENDER:|राउर}} योगदान के एगो लिस्ट",
        "tooltip-pt-login": "रउआ के खाता मे प्रवेश (लॉग इन) खातिर उत्साहित कइल जात बा, बाकि ई जरूरी नइखे",
        "tooltip-pt-logout": "लॉग आउट",
        "tooltip-pt-createaccount": "हमनी के सुझाव बा की आप खाता बनाईं आ लॉग इन करीं, बाकी ई जरूरी नइखे",
        "tooltip-ca-talk": "सामग्री पन्ना की बारे में बात-चीत",
-       "tooltip-ca-edit": "रà¤\89à¤\86 à¤\8f à¤ªà¤¨à¥\8dना à¤\95à¥\87 à¤¸à¤\82पादन à¤\95र à¤¸à¤\95त à¤¬à¤¾à¤¨à¥\80। à¤ªà¤¨à¥\8dना à¤¸à¤¹à¥\87à¤\9cà¥\87 à¤¸à¥\87 à¤ªà¤¹à¤¿à¤²à¥\87 à¤¨à¤®à¥\82ना  à¤¦à¥\87à¤\96ाà¤\88à¤\82 à¤¬à¤\9fन à¤\95à¥\87 à¤\87सà¥\8dतà¥\87माल à¤\95रà¥\80à¤\82।",
+       "tooltip-ca-edit": "à¤\8f à¤ªà¤¨à¥\8dना à¤\95à¥\87 à¤¸à¤\82पादन à¤\95रà¥\80à¤\82",
        "tooltip-ca-addsection": "एगो नया खंड शुरु करीं",
        "tooltip-ca-viewsource": "ए पन्ना के सुरक्षित कइ दिहल गइल बा। आप एकर स्रोत देख सकत बानी।",
        "tooltip-ca-history": "ए पन्ना के पछिला संशोधन",
        "tooltip-t-whatlinkshere": "इहाँ जुड़े वाला सब विकि पन्नवन के लिस्ट",
        "tooltip-t-recentchangeslinked": "ए पन्ना से जुड़ल पन्नवन पर तुरंत भइल बदलाव",
        "tooltip-feed-atom": "ए पन्ना खातिर एटम फीड",
-       "tooltip-t-contributions": "ए सदस्य के कुल योगदान के लिस्ट",
+       "tooltip-t-contributions": "{{GENDER:$1|एह सदस्य}} के योगदान के एक ठो लिस्ट",
        "tooltip-t-upload": "फाइल अपलोड करीं",
        "tooltip-t-specialpages": "खास पन्नवन के लिस्ट",
        "tooltip-t-print": "ए पन्ना के छापे लायक संस्करण",
        "tooltip-t-permalink": "ए पन्ना के संशोधन खातिर स्थायी कड़ी।",
        "tooltip-ca-nstab-main": "सामग्री पन्ना देखीं",
        "tooltip-ca-nstab-user": "सदस्य-पन्ना देखीं",
-       "tooltip-ca-nstab-special": "à¤\88 à¤\8fà¤\97à¥\8b à¤\96ास à¤ªà¤¨à¥\8dना à¤¹, à¤°à¤\89à¤\86à¤\81 à¤\8f à¤ªà¤¨à¥\8dना à¤\95à¥\87 à¤¸à¤\82पादन à¤¨à¤\87à¤\96à¥\80à¤\82 à¤\95र à¤¸à¤\95त",
+       "tooltip-ca-nstab-special": "à¤\88 à¤\8fà¤\97à¥\8b à¤\96ास à¤ªà¤¨à¥\8dना à¤¹, à¤\8fà¤\95र à¤¸à¤\82पादन à¤¨à¤¾ à¤¹à¥\8b à¤¸à¤\95à¥\87ला",
        "tooltip-ca-nstab-image": "फाइल के पन्ना देखीं",
-       "tooltip-ca-nstab-template": "साà¤\81à¤\9aा देखीं",
+       "tooltip-ca-nstab-template": "à¤\9fà¥\87मà¥\8dपलà¥\87à¤\9f देखीं",
        "tooltip-ca-nstab-category": "श्रेणी के पन्ना देखीं",
        "tooltip-save": "बदलाव के सहेजीं",
        "tooltip-preview": "आपन द्वारा कियल गइल बदलाव के देखीं, संजोये से पहले ईका इस्तेमाल करीं!",
        "logentry-delete-delete": "$1 द्वारा पन्ना $3 {{GENDER:$2|हटा}} दिहल गइल",
        "revdelete-restricted": "प्रबंधक पर प्रतिबंध लागू",
        "revdelete-unrestricted": "प्रबंधक पर से प्रतिबंध समाप्त",
+       "logentry-move-move": "$1 पन्ना $3 के $4 पर {{GENDER:$2|स्थानांतरण कइलें}}",
        "logentry-newusers-create": "खाता $1 {{GENDER:$2|बनावल गइल}}",
        "revdelete-summary": "सारांश संपादन",
        "searchsuggest-search": "खोजीं",
index a5c5a14..4921d09 100644 (file)
        "passwordreset-emailelement": "ব্যবহারকারী নাম: \n$1\n\nঅস্থায়ী পাসওয়ার্ড: \n$2",
        "passwordreset-emailsentemail": "যদি এই ই-মেইল ঠিকানা আপনার অ্যাকাউন্টের সাথে সংযুক্ত করা থাকে, তাহলে একটি পাসওয়ার্ড বদলের ইমেইল পাঠানো হবে।",
        "passwordreset-emailsentusername": "যদি এই ব্যবহারকারী নামের সাথে ই-মেইল ঠিকানা সংযুক্ত করা থাকে, তাহলে একটি পাসওয়ার্ড বদলের ইমেইল পাঠানো হবে।",
-       "passwordreset-emailsent-capture": "স্মরণ করিয়ে দেয়ার জন্য একটি ইমেইল করা হয়েছে, যা নিচে দেখানো হচ্ছে।",
-       "passwordreset-emailerror-capture": "স্মরণ করিয়ে দেয়ার জন্য একটি ইমেইল তৈরী করা হয়েছিল, যা নিচে দেখানো হচ্ছে, তবে $1 {{GENDER:$2|ব্যবহারকারীকে}} এটি পাঠানো যায়নি!",
        "passwordreset-nocaller": "একটি আহ্বানকারী প্রদান করা আবশ্যক",
        "passwordreset-nosuchcaller": "আহ্বানকারীর অস্তিত্ব নেই: $1",
        "passwordreset-invalideamil": "ভুল ইমেইল ঠিকানা",
        "passwordreset-nodata": "একটি ব্যবহারকারীর নাম বা একটি ইমেল ঠিকানা দুটির একটিও সরবরা দেয়া হয়নি",
        "changeemail": "ই-মেইল ঠিকানা পরিবর্তন বা বাতিল",
        "changeemail-header": "আপনার ইমেল ঠিকানা পরিবর্তন করতে এই ফরমটি পূরণ করুন। আপনি যদি আপনার একাউন্ট থেকে যে কোন ইমেল ঠিকানার এসোসিয়েশন অপসারণ করতে চান, তাহলে ফরমটি জমা দেওয়ার সময় নতুন ইমেইল ঠিকানা খালি রাখুন।",
-       "changeemail-passwordrequired": "এই পরিবর্তন নিশ্চিত করতে আপনাকে আপনার পাসওয়ার্ড লিখতে হবে।",
        "changeemail-no-info": "এই পাতাটিতে সরাসরি প্রবেশাধিকার পেতে আপনাকে অবশ্যই প্রবেশ করতে হবে।",
        "changeemail-oldemail": "বর্তমান ই-মেইল ঠিকানা:",
        "changeemail-newemail": "নতুন ই-মেইল ঠিকানা:",
        "undo-nochange": "সম্পাদনাটি পূর্বেই বাতিল করা হয়েছে।",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|আলাপ]])-এর সম্পাদিত $1 নম্বর সংশোধনটি বাতিল করা হয়েছে",
        "undo-summary-username-hidden": "একজন লুকানো ব্যবহারকারী $1 সংশোধন পুনরায় ফিরিয়ে এনেছেন",
-       "cantcreateaccounttitle": "অ্যাকাউন্ট তৈরি করা যাবে না",
        "cantcreateaccount-text": "[[User:$3|$3]] এই আইপি ঠিকানা('''$1''') থেকে অ্যাকাউন্ট সৃষ্টিতে বাধা দিয়েছেন।\n\n$3-এর দেয়া কারণ হল ''$2''",
        "cantcreateaccount-range-text": "[[User:$3|$3]] কর্তৃক আইপি ঠিকানার ব্যাপ্তি <strong>$1</strong>-এর মধ্যে অ্যাকাউন্ট তৈরি করা অবরুদ্ধ করা হয়েছে। যাতে আপনার আইপি ঠিকানাও (<strong>$4</strong>) রয়েছে। \n\n$3 কর্তৃক <em>$2</em> কারণ দেখানো হয়েছে।",
        "viewpagelogs": "এই পাতার জন্য লগগুলো দেখুন",
        "log-action-filter-rights-autopromote": "স্বয়ংক্রিয় পরিবর্তন",
        "log-action-filter-upload-upload": "নতুন আপলোড",
        "log-action-filter-upload-overwrite": "পুনঃআপলোড",
+       "authmanager-create-from-login": "আপনার একাউন্ট তৈরি করতে, নীচের ক্ষেত্রগুলি পূরণ করুন।",
        "authmanager-authplugin-setpass-failed-title": "পাসওয়ার্ড পরিবর্তন ব্যর্থ হয়েছে",
        "authmanager-authplugin-setpass-bad-domain": "অবৈধ ডোমেইন।",
        "authmanager-autocreate-noperm": "স্বয়ংক্রিয় অ্যাকাউন্ট সৃষ্টি মঞ্জুরিপ্রাপ্ত নয়।",
index 2c0b040..ee07df4 100644 (file)
        "passwordreset-emailtext-user": "Korisnik $1 na {{SITENAME}} je zatražio podsjetnik o detaljima Vašeg računa za {{SITENAME}} ($4). Sljedeći {{PLURAL:$3|korisnički račun je|korisnički računi su}} povezani s ovom e-mail adresom:\n\n$2\n\n{{PLURAL:$3|Ova privremena šifra|Ove privremene šifre}} će isteći za {{PLURAL:$5|jedan dan|$5 dana}}.\nTrebate se prijaviti i odabrati novu šifru. Ako je neko drugi napravio ovaj zahtjev, ili ako ste se sjetili Vaše originalne šifre, a ne želite je više promijeniti, možete zanemariti ovu poruku i nastaviti koristiti staru šifru.",
        "passwordreset-emailelement": "Korisničko ime: \n$1\n\nPrivremena šifra: \n$2",
        "passwordreset-emailsentemail": "Ako je ovo adresa e-pošte s kojom ste registrirali ovaj račun, podsjetnik šifre će vam biti poslan na vašu adresu e-pošte.",
-       "passwordreset-emailsent-capture": "Poslan je podsjetnik preko e-pošte (prikazano ispod).",
-       "passwordreset-emailerror-capture": "E-poruka za resetiranje lozinke, prikazano ispod, poslana je, ali slanje {{GENDER:$2|korisniku|korisnici}} nije uspjelo: $1",
        "changeemail": "Promjena ili uklanjanje e-adrese",
        "changeemail-header": "Ispunite sljedeći formular da biste promijenili adresu e-pošte. Ako želite ukloniti postojeću adresu e-pošte s vašeg korisničkog računa, pri ispunjavanju formulara, polje nove adrese e-pošte ostavite prazno.",
-       "changeemail-passwordrequired": "Morat ćete unijeti šifru da biste potvrdili ovu izmjenu.",
        "changeemail-no-info": "Morate biti prijavljeni za direktan pristup ovoj stranici.",
        "changeemail-oldemail": "Trenutna adresa e-pošte:",
        "changeemail-newemail": "Nova adresa e-pošte:",
        "minoredit": "Ovo je manja izmjena",
        "watchthis": "Prati ovu stranicu",
        "savearticle": "Sačuvaj stranicu",
+       "publishpage": "Objavi stranicu",
+       "publishchanges": "Objavi izmjene",
        "preview": "Pregled stranice",
        "showpreview": "Prikaži izgled",
        "showdiff": "Prikaži izmjene",
        "undo-nochange": "Izgleda da je izmjena već vraćena.",
        "undo-summary": "Poništena izmjena $1 {{GENDER:$2|korisnika|korisnice}} [[Special:Contributions/$2|$2]] ([[User talk:$2|razgovor]])",
        "undo-summary-username-hidden": "Poništi izmjenu $1 od skrivenog korisnika",
-       "cantcreateaccounttitle": "Nije moguće napraviti korisnički račun",
        "cantcreateaccount-text": "Pravljenje korisničkog računa sa ove IP adrese ('''$1''') je blokirano od strane [[User:$3|$3]].\n\nRazlog koji je naveo $3 je ''$2''",
        "cantcreateaccount-range-text": "Pravljenje računa sa IP adresa u rasponu <strong>$1</strong>, koji uključuje i vašu IP adresu (<strong>$4</strong>), je blokirao korisnik [[User:$3|$3]].\n\nNavedeni razlog korisnika $3 je <em>$2</em>",
        "viewpagelogs": "Pogledaj zapisnike ove stranice",
index 965b9b3..8e71647 100644 (file)
        "passwordreset-emailelement": "Nom d'usuari: \n$1\n\nContrasenya temporal: \n$2",
        "passwordreset-emailsentemail": "Si aquesta adreça electrònica està associada al vostre compte, s’enviarà un missatge de restabliment de contrasenya.",
        "passwordreset-emailsentusername": "Si existeix una adreça electrònica associada a aquest nom d'usuari, s’hi enviarà un missatge de reestabliment de contrasenya.",
-       "passwordreset-emailsent-capture": "S'ha enviat un correu electrònic de reinicialització de contrasenya, tal com es mostra a continuació.",
-       "passwordreset-emailerror-capture": "S'ha generat un correu electrònic de renovació de contrasenya, que es mostra a continuació, però ha fallat l'enviament a {{GENDER:$2:l'usuari|la usuària}}: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|S'ha enviat el correu|S'han enviat els correus}} de restabliment de {{PLURAL:$1|contrasenya|contrasenyes}}. A continuació es mostra {{PLURAL:$1|l'usuari i contrasenya|la llista d'usuaris i contrasenyes}}.",
        "passwordreset-invalideamil": "Adreça de correu electrònic no vàlida",
        "passwordreset-nodata": "No s'ha proporcionat cap nom d'usuari ni adreça electrònica",
        "changeemail": "Canvia o elimina l’adreça electrònica",
        "changeemail-header": "Empleneu aquest formulari per canviar la vostra adreça electrònica. Si voleu eliminar qualssevol associacions d’adreces electròniques del vostre compte, deixeu en blanc el camp i envieu el formulari.",
-       "changeemail-passwordrequired": "Cal que introduïu la vostra contrasenya per confirmar el canvi.",
        "changeemail-no-info": "Heu d'entrar en un compte d'usuari per accedir directament a aquesta pàgina.",
        "changeemail-oldemail": "Adreça electrònica actual:",
        "changeemail-newemail": "Adreça electrònica nova:",
        "undo-nochange": "Sembla que ja s'ha desfet la modificació.",
        "undo-summary": "Es desfà la revisió $1 de [[Special:Contributions/$2|$2]] ([[User talk:$2|Discussió]])",
        "undo-summary-username-hidden": "Desfés la revisió $1 d'un usuari ocult",
-       "cantcreateaccounttitle": "No es pot crear el compte",
        "cantcreateaccount-text": "[[User:$3|$3]] ha bloquejat la creació de comptes des d'aquesta adreça IP ('''$1''').\n\nEl motiu donat per $3 és ''$2''",
        "cantcreateaccount-range-text": "La creació de comptes des de les adreces IP en el rang <strong>$1</strong>, que inclou la vostra adreça IP (<strong>$4</strong>), ha estat blocada per [[User:$3|$3]].\n\nEl motiu donat per $3 és <em>$2</em>",
        "viewpagelogs": "Visualitza els registres d'aquesta pàgina",
        "action-applychangetags": "aplica les etiquetes juntament amb els canvis",
        "action-changetags": "afegeix i elimina etiquetes a les revisions i les entrades de registre individuals",
        "action-deletechangetags": "eliminar etiquetes des de la base de dades",
+       "action-purge": "purga la pàgina",
        "nchanges": "$1 {{PLURAL:$1|canvi|canvis}}",
        "enhancedrc-since-last-visit": "$1 {{PLURAL:$1|des de la darrera visita}}",
        "enhancedrc-history": "historial",
index c8efd12..052c3ce 100644 (file)
        "about": "سەبارەت",
        "article": "بابەت",
        "newwindow": "(لە پەڕەیەکی نوێدا دەکرێتەوە)",
-       "cancel": "ھەڵیوەشێنەوە",
+       "cancel": "ھەڵوەشاندنەوە",
        "moredotdotdot": "زیاتر",
        "morenotlisted": "ئەم لیستەیە تەواو نییە",
        "mypage": "پەڕە",
        "mainpage": "دەستپێک",
        "mainpage-description": "دەستپێک",
        "policy-url": "Project: سیاسەت",
-       "portal": "دەروازەی کۆمەڵگا",
+       "portal": "دەروازەی کۆمەڵگە",
        "portal-url": "Project:دەروازەی کۆمەڵگا",
        "privacy": "سیاسەتی تایبەتێتی",
        "privacypage": "Project:پاراستنی زانیارییەکان",
        "youhavenewmessagesmulti": "لە $1 دا پەیامی نوێت ھەیە",
        "editsection": "دەستکاری",
        "editold": "دەستکاری",
-       "viewsourceold": "سÛ\95رÚ\86اÙ\88Û\95Ú©Û\95Û\8c Ø¨Ø¨Û\8cÙ\86ە",
+       "viewsourceold": "بÛ\8cÙ\86Û\8cÙ\86Û\8c Ø³Û\95رÚ\86اÙ\88ە",
        "editlink": "دەستکاری",
-       "viewsourcelink": "سÛ\95رÚ\86اÙ\88Û\95Ú©Û\95Û\8c Ø¨Ø¨Û\8cÙ\86ە",
+       "viewsourcelink": "بÛ\8cÙ\86Û\8cÙ\86Û\8c Ø³Û\95رÚ\86اÙ\88ە",
        "editsectionhint": "دەستکاریکردنی بەش: $1",
-       "toc": "Ù¾Û\8eرست",
+       "toc": "Ù\86اÙ\88Û\95Ú\95Û\86Ú©",
        "showtoc": "نیشانیبدە",
        "hidetoc": "بیشارەوە",
        "collapsible-collapse": "کۆی بکەوە",
        "nstab-user": "پەڕەی بەکارھێنەر",
        "nstab-media": "میدیا",
        "nstab-special": "پەڕەی تایبەت",
-       "nstab-project": "پەڕەی پرۆژە",
+       "nstab-project": "پەڕەی پڕۆژە",
        "nstab-image": "پەڕگە",
        "nstab-mediawiki": "پەیام",
        "nstab-template": "داڕێژە",
        "perfcached": "داتای خوارەوە پاشەکەوتکراوەیە و لەوانەیە بەڕۆژنەکرابێتەوە. لانی زۆر {{PLURAL:$1|یەک ئەنجام|$1 ئەنجام}} لە cacheدا لەبەردەستدایە.",
        "perfcachedts": "داتای خوارەوە cacheکراوە و دوایین جار لە $1 نوێ کراوەتەوە. لە cacheدا لانی زۆر {{PLURAL:$4|یەک ئەنجام|$4 ئەنجام}} لەبەردەستە.",
        "querypage-no-updates": "تازەکردنەوەکان بۆ ئەم پەڕە لە حاڵی ئێستادا ناچالاک کراوەتەوە.\nداتای ئێرە دەسبەجێ تازە ناکرێتەوە.",
-       "viewsource": "سÛ\95رÚ\86اÙ\88Û\95Ú©Û\95Û\8c Ø¨Ø¨Û\8cÙ\86ە",
+       "viewsource": "بÛ\8cÙ\86Û\8cÙ\86Û\8c Ø³Û\95رÚ\86اÙ\88ە",
        "viewsource-title": "سەرچاوەی $1 ببینە",
        "actionthrottled": "چالاکی پێشی پێ گیرا",
        "actionthrottledtext": "بە مەبەستی پێشگریی لە سپەم، ڕێگە نادرێت تۆ لە ماوەیەکی کورت دا لە سەر یەک ئەمە زۆر جار ئەنجام بدەی، وە ئیستا تۆ لە ڕادە بەدەرت کردووە.\nتکایە پاش چەند خولەک دووبارە تاقی بکەوە.",
        "passwordreset-emailtext-user": "‫بەکارھێنەر $1 لە {{SITENAME}} ڕیسێتکردنەوەی تێپەڕوشەکەت لە {{SITENAME}}دا ($4) کردووە. {{PLURAL:$3|ھەژماری بەکارھێنەریی ژێرەوە پەیوەندیی ھەیە|ھەژمارە بەکارھێنەرییەکانی ژێرەوە پەیوەندییان ھەیە}} بەم ناونیشانەی ئیمەیلەوە:\n\n$2\n\n{{PLURAL:$3|ئەم تێپەڕوشە کاتییە|ئەم تێپەڕوشە کاتییانە}} لە {{PLURAL:$5|ڕۆژێک|$5 ڕۆژ}}دا بەسەردەچێت.\nدەبێ بچیتە ژوورەوە و ھەر ئێستا تێپەڕوشەیەکی نوێ ھەڵبژێریت. ئەگەر کەسێکی تر ئەم داواکارییەی کردووە، یان ئەگەر تێپەڕوشە سەرەتاییەکەت ھاتووەتەوە بیرت و ئیتر ناتەوێ بیگۆڕی، \nدەتوانی گوێ بەم پەیامە نەدەیت و ھەر لە تێپەڕوشە کۆنەکەت کەڵک وەربگریت.",
        "passwordreset-emailelement": "ناوی بەکارھێنەری: \n$1\n\nتێپەڕوشەی کاتی: \n$2",
        "passwordreset-emailsentemail": "ئیمەیلێکی ڕیسێتکردنەوەی تێپەڕوشە نێردرا.",
-       "passwordreset-emailsent-capture": "ئیمەیلێکی ڕیسێتکردنەوەی تێپەڕوشە نێردرا، کە لە ژێرەوە نیشان دراوە.",
-       "passwordreset-emailerror-capture": "ئیمەیلێکی ڕیسێتکردنەوەی تێپەڕوشە نێردرا، کە لە ژێرەوە نیشان دراوە، بەڵام ناردنەکەی بۆ {{GENDER:$2|بەکارھێنەر}} سەرکەوتوو نەبوو: $1",
        "changeemail": "گۆڕینی ناونیشانی ئیمەیل",
        "changeemail-header": "ناونیشانی ئیمەیلی ھەژمار بگۆڕە",
        "changeemail-no-info": "بۆ گەیشتنی راستەوخۆ بەم پەڕە دەبێت بچیتە ژوورەوە.",
        "image_tip": "وێنەی نێو دەق",
        "media_sample": "نموونە.ogg",
        "media_tip": "لینکی پەڕگە",
-       "sig_tip": "ئیمزاکەت بە مۆری ڕێکەوتەوە",
+       "sig_tip": "واژووەکەت بە مۆری ڕێکەوتەوە",
        "hr_tip": "هێڵی ئاسۆیی (دەگمەن بەکاری بێنە)",
        "summary": "کورتەی دەستکاری:",
        "subject": "بابەت/سەردێڕ:",
        "undo-failure": "لەبەر کێشەی دەست‌تێ‌وەردان، ناتوانی دەستکاریەکە ئەنجام‌نەدراو بکەیت.",
        "undo-norev": "ناتوانی دەستکاریەکە ئەنجام‌نەدراو بکەی لەبەر ئەوەی بوونی نیە یا سڕدراوەتەوە.",
        "undo-summary": "گەڕاندنەوەی پێداچوونەوەی $1 لە لایەن [[Special:Contributions/$2|$2]] ([[User talk:$2|لێدوان]])",
-       "cantcreateaccounttitle": "ناتوانرێت هەژمار دروست بکرێت",
        "cantcreateaccount-text": "درووست‌کردنی هەژمارە بۆ ناونیشانی ئای‌پی ('''$1''') لە لایەن [[User:$3|$3]] داخراوە.<br /><br />\n$3 هۆکاری \"$2\" خستوەتەڕوو",
        "viewpagelogs": "لۆگەکانی ئەم پەڕەیە ببینە",
        "nohistory": "هیچ مێژوویەکی دەستکاری نییە بۆ ئەم پەڕەیە.",
        "upload-misc-error-text": "هەڵەیەکی نەناسراو لە کاتی بارکردن ڕووی‌دا.\nتکایە لە درووست‌بوون و دەست‌پێ گەیشتنی URL ئەرخەیان ببە و دیسان تاقی‌بکەوە.\nگەر کێشەکە هەر بەردەوام بوو پەیوەندی بکە بە [[Special:ListUsers/sysop|بەڕێوبەر]].",
        "upload-too-many-redirects": "URL ڕەوانەکەری زۆری لەخۆ گرتووە",
        "upload-http-error": "هەڵەیەکی HTTP ڕووئ داوە: $1",
+       "upload-dialog-button-cancel": "ھەڵوەشاندنەوە",
        "upload-dialog-button-upload": "بارکردن",
+       "upload-form-label-own-work": "ئەمە کاری خۆمە",
        "backend-fail-stream": "نەکرا پەڕگەی $1 بنێردرێت.",
        "backend-fail-notexists": "پەڕگەی $1 بوونی نییە.",
        "backend-fail-delete": "نەکرا پەڕگەی $1 بسڕدرێتەوە.",
        "license-nopreview": "(پێشبینین ئامادەی کەڵک وەرگرتن نییە)",
        "upload_source_url": " (URLـی بەکار، بۆ دەست‌پێگەیشتنی  گشتی)",
        "upload_source_file": "(پەڕگەی ھەڵبژێرراوت لەسەر کۆمپیوتەرەکەت)",
-       "listfiles-delete": "بÛ\8cسÚ\95ەوە",
+       "listfiles-delete": "سÚ\95Û\8cÙ\86ەوە",
        "listfiles-summary": "ئەم پەڕە تایبەتە ھەموو پەڕگە بارکراوەکان نیشان دەدات.",
        "listfiles_search_for": "بگەڕێ بۆ ناوی میدیای:",
        "imgfile": "پەڕگە",
        "duplicatesoffile": "ئەم {{PLURAL:$1|پەڕگە دووبارەکرنەوەیەکی|پەڕگانە دووبارەکردنەوەی}} ئەم پەڕگەن ([[Special:FileDuplicateSearch/$2|وردەکاری زیاتر]]):",
        "sharedupload": "ئەم پەڕگە لە $1ەوەیە و لەوە دەچێ لە پرۆژەکانی دیکەش بەکار ببرێت.",
        "sharedupload-desc-there": "ئەم پەڕگە لە $1ەوەیە و لەوە دەچێ لە پرۆژەکانی دیکەش بەکار ببرێت.\nتکایە بۆ زانیاریی زیاتر چاو بکە لە [$2 لاپەڕەی ناساندنی پەڕگە].",
-       "sharedupload-desc-here": "ئەم پەڕگە لە $1ەوەیە و لەوانەیە لە پرۆژەکانی دیکەش بەکار ھاتبێت.\nپێناسەکەی لەسەر [$2 پەڕەی وەسفی پەڕگەکە] لە خوارەوە نیشان دراوە.",
+       "sharedupload-desc-here": "ئەم پەڕگە لە $1ەوەیە و لەوانەیە لە پڕۆژەکانی دیکەش بەکار ھاتبێت.\nپێناسەکەی لەسەر [$2 پەڕەی وەسفی پەڕگەکە] لە خوارەوە نیشان دراوە.",
        "filepage-nofile": "پەڕگەیەک بەم ناوە نیە.",
        "filepage-nofile-link": "پەڕگەیەک بەم ناوە نیە بەڵام دەتوانی [$1 باری بکەی].",
        "uploadnewversion-linktext": "وەشانێکی نوێی ئەم پەڕگەیە بار بکە",
        "suppress": "چاودێری",
        "apisandbox-unfullscreen": "نیشاندانی پەڕە",
        "booksources": "سەرچاوەکانی کتێب",
-       "booksources-search-legend": "بۆ سەرچاوەی کتێب بگەڕێ",
+       "booksources-search-legend": "گەڕان بۆ سەرچاوەکانی کتێب",
        "booksources-search": "بگەڕێ",
        "booksources-text": "لە خوارەوە لیستێک لە بەستەر بۆ ماڵپەڕهایەک کە کتێبی نوێ و بەکارهێنراو دەفرۆشێت و لەوانەیە لەوێ زانیاریی زیاترت دەست‌کەوێت سەبارەت بەو کتێبانەی لە دووی دەگەڕیت:",
        "booksources-invalid-isbn": "ISBN دراو لەوە ناچی بەکار بێت، سەرنج بدە لە کاتی کۆپی کردن لە سەرچاوە تووشی هەڵە نوبوبێت.",
        "logempty": "هیچ بابەتێکی هاوتا لە لۆگەکاندا نەدۆزرایەوە.",
        "log-title-wildcard": "گەڕانی ئەو سەرناوانە بەم دەقەوە دەست پێدەکەن",
        "showhideselectedlogentries": "دیاریکردنی بابەتە ھەڵبژێردراوەکانی لۆگ بگۆڕە",
+       "checkbox-all": "ھەموو",
        "checkbox-none": "هیچ",
        "allpages": "ھەموو پەڕەکان",
        "nextpage": "پەڕەی پاشەوە ($1)",
        "usermessage-summary": "بەجێھێشتنی پەیامی سیستەم",
        "usermessage-editor": "پەیامنێری سیستەم",
        "watchlist": "پێرستی چاودێری",
-       "mywatchlist": "پێرستی چاودێری",
+       "mywatchlist": "پێڕستی چاودێری",
        "watchlistfor2": "بۆ $1 $2",
        "nowatchlist": "لە لیستی چاودێڕییەکانتدا ھیچ نیە.",
        "watchlistanontext": "بۆ دیتن و دەستکاریی بابەتەکانی  ناو پێرستی چاودێرییەکەتدا دەبێ $1.",
        "excontentauthor": "ناوەرۆک ئەمە بوو: «$1» (و تەنیا بەشداربوو «[[Special:Contributions/$2|$2]]» بوو)",
        "exbeforeblank": "ناوەرۆک بەر لە واڵاکردنەوە ئەمە بوو: «$1»",
        "delete-confirm": "سڕینەوەی «$1»",
-       "delete-legend": "بÛ\8cسÚ\95ەوە",
+       "delete-legend": "سÚ\95Û\8cÙ\86ەوە",
        "historywarning": "<strong>ھۆشیار بە:</strong> پەڕەیەک کە خەریکیت دەیسڕیتەوە مێژوویەکی ھەیە بە $1 {{PLURAL:$1|پێداچوونەوە|پێداچوونەوە}}وە:",
        "historyaction-submit": "نیشاندان",
        "confirmdeletetext": "تۆ خەریکی پەڕەیەک بە ھەموو مێژووەکەیەوە دەسڕیتەو.\nتکایە پشتڕاستی بکەوە کە دەتەوێت ئەم کارە بکەی، لە ئاکامەکەی تێدەگەی، و ئەم کارە بە پێی [[{{MediaWiki:Policy-url}}|سیاسەتنامە]] ئەنجام دەدەی.",
        "sp-contributions-username": "ناونیشانی ئایپی یان ناوی‌ بەکارھێنەر:",
        "sp-contributions-toponly": "تەنیا ئەو دەستکارییانە نیشان بدە کە دوایین پێداچوونەوەن",
        "sp-contributions-newonly": "تەنیا ئەو دەستکارییانە نیشان بدە کە دروستکردنی پەڕەن",
+       "sp-contributions-hideminor": "شاردنەوەی دەستکارییە بچووکەکان",
        "sp-contributions-submit": "بگەڕێ",
        "whatlinkshere": "بەستەرەکان بە ئێرەوە",
        "whatlinkshere-title": "ئەو پەڕانەی بەستەریان ھەیە بۆ «$1»",
        "javascripttest": "تاقیکردنەوەی جاڤاسکریپت",
        "tooltip-pt-userpage": "پەڕەی {{GENDER:|تۆ}}",
        "tooltip-pt-anonuserpage": "پەڕەی بەکارھێنەری بۆ ئای‌پی یەکە کە بەناویەوە خەریکی دەستکاری کردنی",
-       "tooltip-pt-mytalk": "پەڕەی لێدوانەکەت",
+       "tooltip-pt-mytalk": "پەڕەی لێدوان",
        "tooltip-pt-anontalk": "لێدوان لەسەر دەستکارییەکان لەم ئایپی ئەدرەسەوە",
        "tooltip-pt-preferences": "{{GENDER:|هەڵبژاردەکانت}}",
-       "tooltip-pt-watchlist": "پێرستی ئەو پەڕانە کە چاودێریی گۆڕانکارییەکانیانی دەکەی",
-       "tooltip-pt-mycontris": "پێرستی بەشدارییەکانت",
+       "tooltip-pt-watchlist": "پێڕستی ئەو پەڕانەی کە چاودێریی گۆڕانکارییەکانیان دەکەیت",
+       "tooltip-pt-mycontris": "پێڕستی بەشدارییەکان",
        "tooltip-pt-login": "پێشنیارت پێدەکرێ بچیتە ژوورەوە؛ ھەرچەندە زۆرت لێناکرێ",
        "tooltip-pt-logout": "دەرچوون",
-       "tooltip-ca-talk": "Ù\84Û\8eدÙ\88اÙ\86 Ø¯Û\95ربارÛ\95Û\8c Ù\86اÙ\88Û\95Ú\95Û\86Ú©Û\8c Ù¾Û\95رÛ\95",
+       "tooltip-ca-talk": "Ù\88تÙ\88Ù\88Û\8eÚ\98 Ø³Û\95بارÛ\95ت Ø¨Û\95 Ù¾Û\95Ú\95Û\95Û\8c Ù\86اÙ\88Û\95Ú\95Û\86Ú©",
        "tooltip-ca-edit": "دەستکاری ئەم پەڕەیە بکە‌",
        "tooltip-ca-addsection": "بەشێکی نوێ دەست پێ بکە",
        "tooltip-ca-viewsource": "ئەم پەڕەیە پارێزراوە.\nئەتوانی سەرچاوەکەی ببینیت",
        "tooltip-n-recentchanges": "لیستی دوایین گۆڕانکارییەکان لەم ویکییەدا",
        "tooltip-n-randompage": "پەڕەیەک بە هەڵکەوت نیشان بدە",
        "tooltip-n-help": "شوێنی تێگەیشتن",
-       "tooltip-t-whatlinkshere": "پێرستی ھەموو پەڕەکانی ویکی کە بەستەر دراون بۆ ئێرە",
+       "tooltip-t-whatlinkshere": "پێڕستی ھەموو پەڕەکانی ویکی کە بەستەر دراون بۆ ئێرە",
        "tooltip-t-recentchangeslinked": "دوایین گۆڕانکارییەکان لەو پەڕانە کە بەگرەوە گرێ دراون",
        "tooltip-feed-rss": "RSS feed بۆ ئەم پەڕە",
        "tooltip-feed-atom": "Atom feed بۆ ئەم پەڕە",
-       "tooltip-t-contributions": "پێرستی بەشدارییەکانی {{GENDER:$1|ئەم بەکارھێنەرە}}",
+       "tooltip-t-contributions": "پێڕستی بەشدارییەکانی {{GENDER:$1|ئەم بەکارھێنەرە}}",
        "tooltip-t-emailuser": "ئیمەیلێک بنێرە بۆ ئەم بەکارھێنەرە",
        "tooltip-t-upload": "پەڕگە بار بکە",
-       "tooltip-t-specialpages": "پێرستی ھەموو پەڕە تایبەتەکان",
+       "tooltip-t-specialpages": "پێڕستی ھەموو پەڕە تایبەتەکان",
        "tooltip-t-print": "وەشانی چاپی ئەم پەڕەیە",
        "tooltip-t-permalink": "گرێدەری ھەمیشەیی بۆ ئەم وەشانەی ئەم پەڕەیە",
        "tooltip-ca-nstab-main": "بینینی پەڕەی ناوەڕۆک",
        "tooltip-ca-nstab-user": "پەڕەی بەکارھێنەر تەماشا بکە",
        "tooltip-ca-nstab-media": "پەڕەی میدیا چاو لێ بکە",
        "tooltip-ca-nstab-special": "ئەمە پەڕەیەکی تایبەتە و دەستکاری ناکرێت",
-       "tooltip-ca-nstab-project": "بینینی پەڕەی پرۆژە",
+       "tooltip-ca-nstab-project": "بینینی پەڕەی پڕۆژە",
        "tooltip-ca-nstab-image": "بینینی پەڕەی پەڕگە",
        "tooltip-ca-nstab-mediawiki": "بینینی پەیامی سیستەم",
        "tooltip-ca-nstab-template": "بینینی قاڵبەکە",
        "tooltip-ca-nstab-help": "بینینی پەڕەی رێنمایی",
-       "tooltip-ca-nstab-category": "پەڕەی پۆلەکە ببینە",
+       "tooltip-ca-nstab-category": "بینینی پەڕەی پۆلەکە",
        "tooltip-minoredit": "ئەمە وەک گۆڕانکارییەکی بچووک دیاری بکە",
        "tooltip-save": "گۆڕانکارییەکانی خۆت پاشکەوت بکە",
        "tooltip-preview": "پێش بینینی گۆڕانکارییەکان، تکایە پێش پاشکەوت کردن ئەمە بەکار بھێنە",
        "tags-active-yes": "بەڵێ",
        "tags-active-no": "نا",
        "tags-edit": "دەستکاری",
+       "tags-delete": "سڕینەوە",
        "tags-hitcount": "$1 {{PLURAL:$1|گۆڕان|گۆڕانکاری}}",
        "comparepages": "پەڕەکان ھەڵسەنگێنە",
        "compare-page1": "پەڕەی ١",
        "logentry-upload-overwrite": "$1 وەشانێکی نوێی $3ی {{GENDER:$2|بار کرد}}",
        "rightsnone": "(ھیچ)",
        "revdelete-summary": "پوختەی دەستکاری",
-       "feedback-cancel": "ھەڵیوەشێنەوە",
+       "feedback-back": "گەڕانەوە",
+       "feedback-cancel": "ھەڵوەشاندنەوە",
        "feedback-close": "کرا",
        "feedback-message": "پەیام:",
        "feedback-subject": "بابەت:",
        "special-characters-group-gujarati": "گوجەراتی",
        "special-characters-group-thai": "تایلەندی",
        "special-characters-group-khmer": "خمێری",
-       "api-error-blacklisted": "هەڵبژێرە ناونیشانی جیاوازتر و واتادارتر.",
+       "log-action-filter-all": "ھەموو",
        "log-action-filter-upload-upload": "بارکردنی نوێ"
 }
index 86a7951..8b0d350 100644 (file)
        "passwordreset-emailelement": "Uživatelské jméno: \n$1\n\nDočasné heslo: \n$2",
        "passwordreset-emailsentemail": "Pokud je u vašeho účtu nastavena tato e-mailová adresa, bude vám zaslán e-mail pro získání nového hesla.",
        "passwordreset-emailsentusername": "Pokud je u tohoto účtu nastavena e-mailová adresa, bude vám zaslán e-mail pro získání nového hesla.",
-       "passwordreset-emailsent-capture": "Byl odeslán e-mail pro získání nového hesla, který je zobrazen níže.",
-       "passwordreset-emailerror-capture": "Byl vygenerován e-mail pro získání nového hesla, který je zobrazen níže, ale {{GENDER:$2|uživateli|uživatelce}} se ho nepodařilo odeslat: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|Byl odeslán e-mail|Byly odeslány e-maily}} pro získání nového hesla. {{PLURAL:$1|Uživatelské jméno a heslo jsou zobrazeny|Seznam uživatelských jmen a hesel je zobrazen}} níže.",
        "passwordreset-emailerror-capture2": "{{GENDER:$2|Uživateli|Uživatelce}} se nepodařilo odeslat e-mail: $1 {{PLURAL:$3|Uživatelské jméno a heslo jsou zobrazeny|Seznam uživatelských jmen a hesel je zobrazen}} níže.",
        "passwordreset-nocaller": "Musí být uveden volající",
        "passwordreset-nodata": "Nebylo zadáno uživatelské jméno ani e-mailová adresa",
        "changeemail": "Změna nebo odstranění e-mailové adresy",
        "changeemail-header": "Vyplněním tohoto formuláře můžete změnit svou e-mailovou adresu. Pokud chcete ze svého účtu odstranit vazbu na všechny e-mailové adresy, ponechte při odeslání formuláře novou e-mailovou adresu prázdnou.",
-       "changeemail-passwordrequired": "Pro potvrzení této změny musíte zadat své heslo.",
        "changeemail-no-info": "K této stránce mají přímý přístup jen přihlášení uživatelé.",
        "changeemail-oldemail": "Stávající e-mailová adresa:",
        "changeemail-newemail": "Nová e-mailová adresa:",
        "undo-nochange": "Zdá se, že editace již byla zrušena.",
        "undo-summary": "Zrušena verze $1 od uživatele [[Special:Contributions/$2|$2]] ([[User talk:$2|diskuse]])",
        "undo-summary-username-hidden": "Zrušena verze $1 od skrytého uživatele",
-       "cantcreateaccounttitle": "Nelze vytvořit uživatelský účet",
        "cantcreateaccount-text": "Zakládání nových účtů z této IP adresy (<strong>$1</strong>) bylo zablokováno {{GENDER:$3|uživatelem|uživatelkou}} [[User:$3|$3]].\n\n$3 uvádí toto zdůvodnění: <em>$2</em>",
        "cantcreateaccount-range-text": "Zakládání nových účtů z IP adres v rozsahu <strong>$1</strong>, který obsahuje i vaši IP adresu (<strong>$4</strong>), bylo zablokováno {{GENDER:$3|uživatelem|uživatelkou}} [[User:$3|$3]].\n\n$3 uvádí toto zdůvodnění: <em>$2</em>",
        "viewpagelogs": "Zobrazit protokolovací záznamy k této stránce",
        "undeletehistorynoadmin": "Tato stránka byla smazána. Důvod smazání je uveden níže, spolu s informacemi o uživatelích, kteří tuto stránku před smazáním editovali. Samotný text stránky je dostupný pouze správcům.",
        "undelete-revision": "Smazaná verze stránky $1 (z $4 dne $5) od uživatele $3:",
        "undeleterevision-missing": "Nesprávná nebo chybějící revize. Možná máte špatný odkaz, nebo revize byla obnovena či odstraněna z archivu.",
+       "undeleterevision-duplicate-revid": "Nebylo možné obnovit {{PLURAL:$1|jednu revizi|$1 revize|$1 revizí}}, protože {{PLURAL:$1|její|jejich}} <code>rev_id</code> již {{PLURAL:$1|bylo obsazeno|byla obsazena}}.",
        "undelete-nodiff": "Nebyla nalezena žádná předchozí verze.",
        "undeletebtn": "Obnovit",
        "undeletelink": "prohlédnout/obnovit",
        "undeletedrevisions": "{{PLURAL:$1|Obnovena jedna verze|Obnoveny $1 verze|Obnoveno $1 verzí}}",
        "undeletedrevisions-files": "{{PLURAL:$1|Obnovena jedna verze|Obnoveny $1 verze|Obnoveno $1 verzí}} a {{PLURAL:$2|jeden soubor|$2 soubory|$2 souborů}}.",
        "undeletedfiles": "{{PLURAL:$1|Obnoven jeden soubor|Obnoveny $1 soubory|Obnoveno $1 souborů}}",
-       "cannotundelete": "Obnovení se nezdařilo:\n$1",
+       "cannotundelete": "Některá nebo všechna obnovení se nezdařila:\n$1",
        "undeletedpage": "<strong>Stránka „$1“ byla obnovena</strong>\n\nZáznam o posledních mazáních a obnoveních najdete v [[Special:Log/delete|knize smazaných stránek]].",
        "undelete-header": "Vizte nedávno smazané stránky v [[Special:Log/delete|knize smazaných stránek]].",
        "undelete-search-title": "Hledání smazaných stránek",
        "sp-contributions-newbies-sub": "Noví uživatelé",
        "sp-contributions-newbies-title": "Příspěvky nových uživatelů",
        "sp-contributions-blocklog": "kniha zablokování",
-       "sp-contributions-suppresslog": "utajené příspěvky uživatele",
-       "sp-contributions-deleted": "smazané editace uživatele",
+       "sp-contributions-suppresslog": "utajené příspěvky {{GENDER:$1|uživatele|uživatelky}}",
+       "sp-contributions-deleted": "smazané editace {{GENDER:$1|uživatele|uživatelky}}",
        "sp-contributions-uploads": "načtené soubory",
        "sp-contributions-logs": "protokolovací záznamy",
        "sp-contributions-talk": "diskuse",
index a1a9953..aca71bb 100644 (file)
        "passwordreset-emailtext-user": "Gofynodd y defnyddiwr $1 ar {{SITENAME}} am gael ailosod ei gyfrinair ar {{SITENAME}}\n($4). Mae'r {{PLURAL:$3||cyfrif|cyfrifon}} canlynol ynghlwm wrth y cyfeiriad e-bost hwn:\n\n$2\n\nBydd y {{PLURAL:$3||cyfrinair|cyfrineiriau}} dros dro hyn yn dod i ben ymhen {{PLURAL:$5||diwrnod|deuddydd|tridiau|$5 diwrnod}}.\nDylech fewngofnodi nawr a dewis cyfrinair newydd. Os mai rhywun arall a ofynodd am ailosod y cyfrinair, neu os ydych wedi cofio eich cyfrinair gwreiddiol, neu os nad ydych am ei newid bellach, gallwch anwybyddu'r neges hon a pharhau i ddefnyddio eich hen gyfrinair.",
        "passwordreset-emailelement": "Enw'r defnyddiwr: \n$1\n\nY cyfrinair dros dro: \n$2",
        "passwordreset-emailsentemail": "Anfonwyd e-bost i ailosod eich cyfrinair atoch.",
-       "passwordreset-emailsent-capture": "Anfonwyd e-bost i ailosod cyfrinair, ac fe'i ddangosir isod.",
-       "passwordreset-emailerror-capture": "Lluniwyd e-bost i ailosod cyfrinair fel ag a welir isod, ond ni lwyddwyd i'w anfon at y {{GENDER:$2|defnyddiwr}}: $1",
        "changeemail": "Newid y cyfeiriad e-bost",
        "changeemail-header": "Cwbwlhewch y ffurflen hon i newid cyfeiriad e-bost y cyfrifi. I ddileu pob cysylltiad i bob cyfeiriad ebost, gadewch e'n wag.",
        "changeemail-no-info": "Ni allwch fynd at y dudalen hon heblaw eich bod wedi mewngofnodi.",
        "undo-nochange": "Ymddengys fod y golygiad wedi ei ddadwneud yn barod.",
        "undo-summary": "Dadwneud y golygiad $1 gan [[Special:Contributions/$2|$2]] ([[User talk:$2|Sgwrs]] | [[Special:Contributions/$2|{{MediaWiki:Contribslink}}]])",
        "undo-summary-username-hidden": "Dadwneud y golygiad $1 gan ddefnyddiwr cudd",
-       "cantcreateaccounttitle": "Yn methu creu cyfrif",
        "cantcreateaccount-text": "Rhwystrwyd y gallu i greu cyfrif ar gyfer y cyfeiriad IP hwn, ('''$1'''), gan [[User:$3|$3]].\n\nY rheswm a roddwyd dros y bloc gan $3 yw ''$2''.",
        "cantcreateaccount-range-text": "Gosododd [[User:$3|$3]] floc ar agor cyfrifon o gyfeiriadau IP yn yr ystod <strong>$1</strong>, sy'n cynnwys eich cyfeiriad IP chi (<strong>$4</strong>).\n\nY rheswm a roddwyd gan $3 yw \"$2\"",
        "viewpagelogs": "Dangos logiau'r dudalen hon",
        "rightslogtext": "Lòg y newidiadau i alluoedd defnyddwyr yw hwn.",
        "action-read": "darllen y dudalen",
        "action-edit": "golygu'r dudalen",
-       "action-createpage": "creu tudalennau",
-       "action-createtalk": "creu tudalennau sgwrs",
+       "action-createpage": "crewch y ddalen hon",
+       "action-createtalk": "crewch y ddalen Sgwrs",
        "action-createaccount": "creu'r cyfrif defnyddiwr hwn",
+       "action-autocreateaccount": "crewch y cyfri defnyddiwr allanol yma",
        "action-history": "gweld hanes y dudalen",
        "action-minoredit": "marcio'r golygiad yn un bach",
        "action-move": "symud y dudalen",
        "action-viewmywatchlist": "gweld eich rhestr wylio",
        "action-viewmyprivateinfo": "gweld eich manylion personol preifat",
        "action-editmyprivateinfo": "golygu eich manylion personol preifat",
+       "action-editcontentmodel": "golygwch y cynnwys",
        "nchanges": "$1 {{PLURAL:$1|newid|newid|newid|newid|newid|o newidiadau}}",
        "enhancedrc-since-last-visit": "$1 {{PLURAL:$1|ers eich ymweliad diwethaf}}",
        "enhancedrc-history": "hanes",
        "apisandbox-submit": "Gwnewch gais",
        "apisandbox-reset": "Clirio",
        "apisandbox-retry": "Ailgeisio",
+       "apisandbox-helpurls": "Dolennau cymorth",
+       "apisandbox-examples": "Engreifftiau",
+       "apisandbox-results": "Canlyniadau",
        "booksources": "Ffynonellau llyfrau",
        "booksources-search-legend": "Chwilier am lyfrau",
        "booksources-search": "Chwilio",
        "logempty": "Does dim eitemau yn cyfateb yn y lòg.",
        "log-title-wildcard": "Chwilio am deitlau'n dechrau gyda'r geiriau hyn",
        "showhideselectedlogentries": "Dewis dangos neu guddio cofnodion lòg",
+       "checkbox-all": "Y cyfan",
+       "checkbox-none": "Dim",
        "allpages": "Pob tudalen",
        "nextpage": "Y bloc nesaf gan ddechrau gyda ($1)",
        "prevpage": "Y bloc cynt gan ddechrau gyda ($1)",
        "activeusers-hidebots": "Cuddio botiau",
        "activeusers-hidesysops": "Cuddio gweinyddwyr",
        "activeusers-noresult": "Dim defnyddwyr i'w cael.",
+       "activeusers-submit": "Dangos defnyddwyr byw",
        "listgrouprights": "Galluoedd grwpiau defnyddwyr",
        "listgrouprights-summary": "Dyma restr o'r grwpiau defnyddwyr sydd i'w cael ar y wici hon, ynghyd â galluoedd aelodau'r gwahanol grwpiau. Cewch wybodaeth pellach am y gwahanol alluoedd ar y [[{{MediaWiki:Listgrouprights-helppage}}|dudalen gymorth]].",
        "listgrouprights-key": "Allwedd:\n* <span class=\"listgrouprights-granted\">Gallu sydd wedi ei roi</span>\n* <span class=\"listgrouprights-revoked\">Gallu sydd wedi ei dynnu yn ôl</span>",
        "listgrouprights-namespaceprotection-header": "Cyfyngiadau parth",
        "listgrouprights-namespaceprotection-namespace": "Parth",
        "listgrouprights-namespaceprotection-restrictedto": "Gallu(oedd) yn caniatau i'r defnyddiwr olygu",
+       "listgrants": "Nawdd",
+       "listgrants-rights": "Hawliau",
        "trackingcategories": "Categoriau tracio",
        "trackingcategories-summary": "Mae'r dudalen hon yn rhestru categoriau tracio sy'n cael eu creu'n otomatig gan feddalwedd MediaWiki. Gellir newid eu henwau drwy addasu'r negeseuon ym mharthenw {{ns:8}}.",
        "trackingcategories-msg": "Categori tracio",
        "sessionfailure": "Mae'n debyg fod yna broblem gyda'ch sesiwn mewngofnodi; diddymwyd y weithred er mwyn diogelu'r sustem rhag ddefnyddwyr maleisus. Gwasgwch botwm 'nôl' eich porwr ac ail-lwythwch y dudalen honno, yna ceisiwch eto.",
        "changecontentmodel-title-label": "Teitl y ddalen",
        "changecontentmodel-reason-label": "Rheswm:",
+       "changecontentmodel-submit": "Newid",
        "protectlogpage": "Lòg diogelu",
        "protectlogtext": "Isod mae rhestr o bob gweithred diogelu (a dad-ddiogelu) tudalen.\nMae'r tudalennau sydd wedi eu diogelu ar hyn o bryd wedi eu rhestri ar y [[Special:ProtectedPages|rhestr tudalennau wedi eu diogelu]].",
        "protectedarticle": "wedi diogelu '[[$1]]'",
        "whatlinkshere-links": "← cysylltiadau",
        "whatlinkshere-hideredirs": "$1 ailgyfeiriadau",
        "whatlinkshere-hidetrans": "$1 cynhwysion",
-       "whatlinkshere-hidelinks": "$1 cysylltau",
+       "whatlinkshere-hidelinks": "$1 dolennau",
        "whatlinkshere-hideimages": "$1 cysylltau ffeiliau",
        "whatlinkshere-filters": "Hidlau",
        "autoblockid": "Awtoflocio #$1",
index 9833f1a..4fb3f7b 100644 (file)
        "passwordreset-emailelement": "Brugernavn: \n$1\n\nMidlertidig adgangskode: \n$2",
        "passwordreset-emailsentemail": "Hvis denne e-mailadresse er knyttet til din konto, så vil en e-mail om nulstilling af adgangskoden blive sendt.",
        "passwordreset-emailsentusername": "Hvis der er en e-mailadresse forbundet med dette brugernavn, så vil en e-mail om nulstilling af adgangskoden blive sendt.",
-       "passwordreset-emailsent-capture": "En e-mail om nulstilling af adgangskode, som vist nedenfor, er blevet sendt.",
-       "passwordreset-emailerror-capture": "En mail om nulstilling af adgangskode, som vist nedenfor, blev genereret, men det lykkedes ikke at sende den til {{GENDER:$2|bruger}}: $1",
        "changeemail": "Ændr eller fjern e-mailadresse",
        "changeemail-header": "Udfyld denne formular for at ændre din e-mailadresse. Hvis du gerne vil fjerne forbindelsen af en e-mailadresse fra din konto, så lad den nye e-mailadresse være blank, når du sender formularen.",
-       "changeemail-passwordrequired": "Du er nødt til at indtaste din adgangskode for at bekræfte denne ændring.",
        "changeemail-no-info": "Du skal være logget på for at komme direkte til denne side.",
        "changeemail-oldemail": "Nuværende e-mailadresse:",
        "changeemail-newemail": "Ny e-mailadresse:",
        "minoredit": "Dette er en mindre ændring",
        "watchthis": "Overvåg denne side",
        "savearticle": "Gem side",
+       "publishpage": "Offentliggør side",
+       "publishchanges": "Offentliggør ændringer",
        "preview": "Forhåndsvisning",
        "showpreview": "Forhåndsvisning",
        "showdiff": "Vis ændringer",
        "undo-nochange": "Ændringen ser ud til allerede at være blevet fjernet.",
        "undo-summary": "Fjerner version $1 af [[Special:Contributions/$2|$2]] ([[User talk:$2|diskussion]])",
        "undo-summary-username-hidden": "Fortryde revision $1 af en skjult bruger",
-       "cantcreateaccounttitle": "Brugerkontoen kan ikke oprettes.",
        "cantcreateaccount-text": "Oprettelsen af en brugerkonto fra IP-adressen ('''$1''') er blevet blokeret af [[User:$3|$3]].\n\nÅrsagen til blokeringen er angivet af $3 som ''$2''",
        "cantcreateaccount-range-text": "Oprettelsen af en brugerkonto fra IP-adresser i intervallet <strong>$1</strong>, som omfatter din IP-adresse (<strong>$4</strong>), er blevet blokeret af [[User:$3|$3]].\n\nÅrsagen angivet af $3 er <em>$2</em>",
        "viewpagelogs": "Vis loglister for denne side",
index 60e8456..49e0a22 100644 (file)
        "passwordreset-emailelement": "Benutzername: \n$1\n\nTemporäres Passwort: \n$2",
        "passwordreset-emailsentemail": "Falls diese E-Mail-Adresse mit deinem Benutzerkonto verknüpft ist, wird eine Passwort-Zurücksetzungs-E-Mail versandt.",
        "passwordreset-emailsentusername": "Falls es eine E-Mail-Adresse gibt, die mit diesem Benutzernamen verknüpft ist, wird eine Passwort-Zurücksetzungs-E-Mail versandt.",
-       "passwordreset-emailsent-capture": "Eine Passwortzurücksetzungs-E-Mail wurde versandt, die unten angezeigt wird.",
-       "passwordreset-emailerror-capture": "Die unten angezeigte Passwortzurücksetzungs-E-Mail wurde generiert, allerdings ist der Versand an {{GENDER:$2|den Benutzer|die Benutzerin}} gescheitert: $1",
        "passwordreset-emailsent-capture2": "Die Passwort-Zurücksetzungs-{{PLURAL:$1|E-Mail wurde|E-Mails wurden}} versandt. {{PLURAL:$1|Der Benutzername und das Passwort|Die Liste der Benutzernamen und Passwörter}} wird unten angezeigt.",
        "passwordreset-emailerror-capture2": "Das Senden der E-Mail an {{GENDER:$2|den Benutzer|die Benutzerin}} ist fehlgeschlagen: $1 {{PLURAL:$3|Der Benutzername und das Passwort|Die Liste der Benutzernamen und Passwörter}} wird unten angezeigt.",
        "passwordreset-nocaller": "Es muss ein Rufer angegeben werden",
        "passwordreset-nodata": "Weder ein Benutzername noch eine E-Mail-Adresse wurde angegeben",
        "changeemail": "E-Mail-Adresse ändern oder entfernen",
        "changeemail-header": "Fülle dieses Formular vollständig aus, um deine E-Mail-Adresse zu ändern. Falls du die Zuweisung einer E-Mail-Adresse zu deinem Benutzerkonto entfernen möchtest, lasse beim Übermitteln des Formulars das Feld für die neue E-Mail-Adresse leer.",
-       "changeemail-passwordrequired": "Du musst dein Passwort eingeben, um diese Änderung zu bestätigen.",
        "changeemail-no-info": "Du musst angemeldet sein, um direkt auf diese Seite zugreifen zu können.",
        "changeemail-oldemail": "Aktuelle E-Mail-Adresse:",
        "changeemail-newemail": "Neue E-Mail-Adresse:",
        "undo-nochange": "Anscheinend wurde diese Bearbeitung bereits rückgängig gemacht.",
        "undo-summary": "Änderung $1 von [[Special:Contributions/$2|$2]] ([[User talk:$2|Diskussion]]) rückgängig gemacht.",
        "undo-summary-username-hidden": "Änderung $1 eines versteckten Benutzers rückgängig gemacht.",
-       "cantcreateaccounttitle": "Das Benutzerkonto kann nicht erstellt werden",
        "cantcreateaccount-text": "Die Erstellung eines Benutzerkontos von der IP-Adresse '''($1)''' aus wurde durch [[User:$3|$3]] gesperrt.\n\nGrund der Sperre: ''$2''",
        "cantcreateaccount-range-text": "Das Erstellen von Benutzerkonten von IP-Adressen im Bereich <strong>$1</strong>, der deine IP-Adresse (<strong>$4</strong>) enthält, wurde von [[User:$3|$3]] gesperrt.\n\nDer angegebene Grund von $3 lautet: <em>$2</em>",
        "viewpagelogs": "Logbücher dieser Seite anzeigen",
        "uploadstash-errclear": "Das Entfernen der vorab gespeicherten Dateien ist fehlgeschlagen.",
        "uploadstash-refresh": "Liste der Dateien aktualisieren",
        "uploadstash-thumbnail": "Vorschaubild ansehen",
+       "uploadstash-exception": "Upload konnte nicht gespeichert werden ($1): „$2“.",
        "invalid-chunk-offset": "Ungültiger Startpunkt",
        "img-auth-accessdenied": "Zugriff verweigert",
        "img-auth-nopathinfo": "Die Angabe PATH_INFO fehlt.\nDer Server ist nicht dafür eingerichtet, diese Information weiterzugeben.\nSie könnte CGI-gestützt sein und kann daher „img_auth“ (Authentifizierung des Dateiaufrufs) nicht unterstützen.\nSiehe auch https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization (englisch).",
        "undeletehistorynoadmin": "Diese Seite wurde gelöscht. Der Löschgrund ist in der Zusammenfassung angegeben,\ngenauso wie Details zum letzten Benutzer, der diese Seite vor der Löschung bearbeitet hat.\nDer aktuelle Text der gelöschten Seite ist nur Administratoren zugänglich.",
        "undelete-revision": "Gelöschte Version von $1 (vom $4 um $5 Uhr), $3:",
        "undeleterevision-missing": "Ungültige oder fehlende Version. Entweder ist der Link falsch oder die Version wurde aus dem Archiv wiederhergestellt oder entfernt.",
+       "undeleterevision-duplicate-revid": "{{PLURAL:$1|Eine Version konnte|$1 Versionen konnten}} nicht wiederhergestellt werden, da ihre <code>rev_id</code> bereits in Verwendung {{PLURAL:$1|ist|sind}}.",
        "undelete-nodiff": "Keine vorhergehende Version vorhanden.",
        "undeletebtn": "Wiederherstellen",
        "undeletelink": "ansehen/wiederherstellen",
        "undeletedrevisions": "{{PLURAL:$1|1 Version wurde|$1 Versionen wurden}} wiederhergestellt",
        "undeletedrevisions-files": "{{PLURAL:$1|1 Version|$1 Versionen}} und {{PLURAL:$2|1 Datei|$2 Dateien}} wurden wiederhergestellt",
        "undeletedfiles": "{{PLURAL:$1|1 Datei wurde|$1 Dateien wurden}} wiederhergestellt",
-       "cannotundelete": "Die Wiederherstellung ist fehlgeschlagen:\n$1",
+       "cannotundelete": "Einige oder alle Wiederherstellungen sind fehlgeschlagen:\n$1",
        "undeletedpage": "'''„$1“''' wurde wiederhergestellt.\n\nIm [[Special:Log/delete|Lösch-Logbuch]] findest du eine Übersicht der gelöschten und wiederhergestellten Seiten.",
        "undelete-header": "Siehe das [[Special:Log/delete|Lösch-Logbuch]] für kürzlich gelöschte Seiten.",
        "undelete-search-title": "Nach gelöschten Seiten suchen",
        "sp-contributions-newbies-sub": "Von neuen Benutzern",
        "sp-contributions-newbies-title": "Benutzerbeiträge von neuen Benutzern",
        "sp-contributions-blocklog": "Sperr-Logbuch",
-       "sp-contributions-suppresslog": "Unterdrückte Benutzerbeiträge",
-       "sp-contributions-deleted": "Gelöschte Beiträge",
+       "sp-contributions-suppresslog": "Unterdrückte {{GENDER:$1|Benutzerbeiträge}}",
+       "sp-contributions-deleted": "Gelöschte {{GENDER:$1|Benutzerbeiträge}}",
        "sp-contributions-uploads": "Hochgeladene Dateien",
        "sp-contributions-logs": "Logbücher",
        "sp-contributions-talk": "Diskussion",
index ce5adea..af785a0 100644 (file)
        "july-date": "Temuz $1",
        "august-date": "Tebaxe $1",
        "september-date": "Keşkelun $1",
-       "october-date": "$1 Cetan",
-       "november-date": "$1 Kelverdan",
+       "october-date": "Tışrino Verên $1",
+       "november-date": "Tışrino Peyên $1",
        "december-date": "Kanun $1",
        "period-am": "AM",
        "period-pm": "PM",
        "redirectedfrom": "($1 ra kırışı yê)",
        "redirectpagesub": "Pela berdışi",
        "redirectto": "Beno hetê:",
-       "lastmodifiedat": "Ena pele tewr peyên roca $1, seate $2 de biya rocaniye.{{MediaWiki bın}}",
+       "lastmodifiedat": "Ena pele tewr peyên roca $1, saeta $2 de biye rocane.",
        "viewcount": "Ena pele {{PLURAL:$1|rae|$1 rey}} vêniya.",
        "protectedpage": "Pela pawıtiye",
        "jumpto": "Şo be:",
        "botpasswords-label-appid": "Nameyê boti:",
        "botpasswords-label-create": "Vıraze",
        "botpasswords-label-update": "Rocane ke",
-       "botpasswords-label-cancel": "Bıterkın",
+       "botpasswords-label-cancel": "Bıtexelne",
        "botpasswords-label-delete": "Bestere",
        "botpasswords-label-resetpassword": "Parola raçarne",
        "botpasswords-label-grants-column": "Dayen",
        "resetpass_forbidden": "parolayi nêvuryayi",
        "resetpass-no-info": "şıma gani hesab akere u hona bıeşke bırese cı",
        "resetpass-submit-loggedin": "Parola bıvurne",
-       "resetpass-submit-cancel": "Bıterkın",
+       "resetpass-submit-cancel": "Bıtexelne",
        "resetpass-wrong-oldpass": "parolayo parola maqbul niyo.\nşıma ya parolaye xo vurnayo ya zi parolayo muwaqqat waşto.",
        "resetpass-recycled": "Parolaya şımaya newiye wa paroloya şımaya verêne ra ferqıne bo.",
        "resetpass-temp-emailed": "E postaya rışyayê yubkoda şıma ronıştış akerdo.  Ronıştışi xo temammkerdışi rê yu parolaya newi lazım a",
        "passwordreset-emailtext-user": "$1 enê karberi, {{SITENAME}}  ra ($4) teferuatê hesab dê şıma  va wa biyaro xo viri. Karbero ke cêrdeyo {{PLURAL:$3|hesaba|eno hesaba}} ena e-posta adresiya aleqey cı esto:\n\n$2\n\n{{PLURAL:$3|ena parola idaretena|ena parola idareten}} {{PLURAL:$5|jew roc|$5  roca}}rêya.\nEna parolaya deqewe de u xorê ju parolaya newi bıweçine. Parolaya şıma emaya şıma viri se  yana  ena e-posta şıma nê weştase u şıma qayıl niye parolaya xo bıvurnese, ena mesacer peygoş bıkerê.",
        "passwordreset-emailelement": "Nameyê karberi: \n$1\n\nParolaya vêrdiye: \n$2",
        "passwordreset-emailsentemail": "Eke na seba hesabê şıma yew adresa e-posteyê qeydına, yew e-posteyê parola nênkerdışi rışiyeno.",
-       "passwordreset-emailsent-capture": "Yew e-posteyê esterıtışê parolayo ke rışiya, no cêr mocniyayo.",
-       "passwordreset-emailerror-capture": "Yew e-posteyê esterıtışê parolayo ke rışiya, no cêr mocniyayo, ema {{GENDER:$2|karber}}i rê rıştış de mıwefeq nêbi: $1",
        "passwordreset-invalideamil": "Adresê eposta raşt niya",
        "changeemail": "E-posta adresa xo wedarne",
        "changeemail-header": "E-posya adresta hesabdê xo bıvurnê",
        "undo-norev": "Vurnayiş tepêya nêgeryeno çunke ya vere cû hewna biyo ya zi ca ra çino.",
        "undo-summary": "Vırnayışê $1'i [[Special:Contributions/$2|$2i]] ([[User talk:$2|Werênayış]]) peyser gırot",
        "undo-summary-username-hidden": "Rewizyona veri $1'i hewada",
-       "cantcreateaccounttitle": "Nêşenay hesab rakerê",
        "cantcreateaccount-text": "Hesabvıraştışê na IP adrese ('''$1''') terefê [[User:$3|$3]] kılit biyo.\n\nSebebo ke terefê $3 ra diyao ''$2''",
        "viewpagelogs": "Seba na pele rê qeydan bımocne",
        "nohistory": "Verê vurnayışanê na pele çıniyo.",
        "mergehistory-empty": "Revizyonî yew nibenê.",
        "mergehistory-done": "$1 ra $3 {{PLURAL:$3|revizyon|revizyoni}} [[:$2]] de {{PLURAL:$3|biyo|biyê}} têmiyan.",
        "mergehistory-fail": "Tarixê pele yew nibeno, ma rica kenê ke pel u wext control bike.",
+       "mergehistory-fail-bad-timestamp": "Mora zemani ravêrdi niya",
+       "mergehistory-fail-invalid-source": "Çime per ravêrdi niya",
+       "mergehistory-fail-invalid-dest": "Hedef per ravêrdi niya",
+       "mergehistory-fail-permission": "Verori yewkerdışi rê mısade çıni yo.",
+       "mergehistory-fail-self-merge": "Çıne u hedef pera zey pê yê",
        "mergehistory-no-source": "Pela çımeyê $1 çıniya.",
        "mergehistory-no-destination": "Pela destinasyoni $1 çini yo.",
        "mergehistory-invalid-source": "Pela çime gani yew seroğê raşt biy.",
        "grant-oversight": "Karberan u ploğyayê revizyona bınımn",
        "grant-patrol": "Perer de vurnayışa çımra ravyarn",
        "grant-protect": "Şeveknayış u wedarıtışê şeveknayışê pelan",
+       "grant-sendemail": "Karberanê binan rê e-posta bırışê",
+       "grant-uploadeditmovefile": "Dosyaya bar ke, bıvurnê  yana berê",
        "grant-uploadfile": "Dosyaya newi bar ke",
        "grant-basic": "Heqê basiti",
        "grant-viewdeleted": "Besteryaya peran u dosyaya bıasne",
        "action-createpage": "Ena perer bıvıraze",
        "action-createtalk": "pelanê werênayışi bıvıraze",
        "action-createaccount": "hesabê nê karberi bıvıraze",
+       "action-autocreateaccount": "nê hesabê karberiyê teberi otomatik vıraze",
+       "action-history": "tarixê na pele bıvêne",
        "action-minoredit": "nê vurnayışi be qıckek işaret ke",
        "action-move": "ena pele bere",
        "action-move-subpages": "ena pele, u pelanê daê bınênan bere",
        "recentchanges-submit": "Bıasne",
        "rcnotefrom": "Cêr de <strong>$2</strong> ra nata {{PLURAL:$5|vurnayışiyê}} asenê (tewr vêşi <strong>$1</strong> asenê) <strong>$3, $4</strong>",
        "rclistfrom": "$3 $2 ra tepiya vurnayışanê neweyan bımocne",
-       "rcshowhideminor": "vurriyayışanê werdiyan $1",
+       "rcshowhideminor": "vurriyayışê werdi $1",
        "rcshowhideminor-show": "Bımocne",
        "rcshowhideminor-hide": "Bınımne",
        "rcshowhidebots": "botan $1",
        "newpages-submit": "Bıasene",
        "newpages-username": "Nameyê karberi:",
        "ancientpages": "Pelê kehenêri",
-       "move": "Bıkırış",
+       "move": "Bıkırışe",
        "movethispage": "Ena pele bıkırışe",
        "unusedimagestext": "Enê dosyey estê, feqet zerrey yew pele de wedardey niyê.\nXo vira mekerê ke, sıteyê webiê bini şenê direkt ebe URLi yew dosya ra gırê bê, u wına şenê verba gurênayışo feal de tiya hewna lista bê.",
        "unusedcategoriestext": "Kategoriyê ke cêr derê, nê bıbê zi, terefê qet madeyan ya zi kategoriyan ra nêgureniyenê.",
        "anonymous": "{{PLURAL:$1|karberê|karberê}} anonimi yê keyepelê {{SITENAME}}i",
        "siteuser": "karberê {{SITENAME}}i $1",
        "anonuser": "karberê anonim o {{SITENAME}}i $1",
-       "lastmodifiedatby": "Ena pele tewr peyên roca $2, $1 de tereftê $3 ra vuriya ya.",
+       "lastmodifiedatby": "Ena per tewr peyên roca $2, $1 de terefê $3 ra vurmaya ya.",
        "othercontribs": "xebatê $1 ıney geriyayo diqqeti/geriyayo nezer.",
        "others": "bini",
        "siteusers": "{{SITENAME}} {{PLURAL:$2|karberê ey|karberanê ey}} $1",
        "fileduplicatesearch-result-1": "Dosyayê ''$1î'' de hem-kopya çini yo.",
        "fileduplicatesearch-result-n": "Dosyayê ''$1î'' de {{PLURAL:$2|1 hem-kopya|$2 hem-kopyayî'}} esto.",
        "fileduplicatesearch-noresults": "Ebe namey \"$1\" ra dosya nêdiyayê.",
-       "specialpages": "Pelê xısusiy",
+       "specialpages": "Pelê xısusiyi",
        "specialpages-note-top": "Kıtabek",
        "specialpages-note": "* Pelê xasê normali.\n* <span class=\"mw-specialpagerestricted\">Pelê xasê nımıtey.</span>",
        "specialpages-group-maintenance": "Raporê pawıtışi",
        "feedback-bugcheck": "Harika! Sadece [xırabina ke $1 ] çınyayışê cı kontrol keno.",
        "feedback-bugnew": "Mı qontrol ke. Xetaya newi xeber ke",
        "feedback-bugornote": "Jew mersela teferruato teknik esta şıma reca malumatê şıma hazıro se [ $1  jew xırab rapor] bıvinê.Zewbi zi, formê cerê xo rê şenê karfiyê. Vatışê xo pela da \"[ $3  $2 ]\", namey karber dê xoya piya u wasteriya karfiye.",
-       "feedback-cancel": "Bıterkın",
+       "feedback-cancel": "Bıtexelne",
        "feedback-close": "Biya star",
        "feedback-error1": "Xeta: API ra neticey ne vıcyay",
        "feedback-error2": "Xeta: Timar kerdış nebı",
index 6d1a32a..cf025f0 100644 (file)
        "passwordreset-emailtext-user": "Wužywaŕ $1 jo anulěrowanje gronidła za {{GRAMMAR:akuzatiw|{{SITENAME}}}} pominał ($4).  {{PLURAL:$3|Slědujuce wužywarske konto jo|Slědujucej wužywarskej konśe stej|Slědujuce wužywarske konta su}} z toś tej e-mailoweju adresu {{PLURAL:$3|zwězane|zwězanej|zwězane}}:\n\n$2\n\n{{PLURAL:$3|Toś to nachylne gronidło spadnjo|Toś tej nachylnej gronidle spadnjotej|Toś te nachylne gronidła spadnu}} za {{PLURAL:$5|jaden źeń|$5 dnja|$5 dny|$5 dnjow}}.\nTy by měł se něnto pśizjawiś a nowe gronidło wustajiś. Jolic něchten drugi jo toś to napšašowanje pósłał, abo jolic sy se zasej na spócetne gronidło spomnjeł a wěcej njocoš jo změniś, móžoš toś to zdźělenje ignorěrowaś a swójo stare gronidło dalej wužywaś.",
        "passwordreset-emailelement": "Wužywarske mě: \n$1\n\nNachylne gronidło: \n$2",
        "passwordreset-emailsentemail": "E-mail za anulěrowanje gronidła jo se pósłała.",
-       "passwordreset-emailsent-capture": "E-mail za anulěrowanje gronidła jo se pósłała, kótaraž pokazujo se dołojce.",
-       "passwordreset-emailerror-capture": "E-mail za anulěrowanje gronidła jo se napórała, kótaraž se dołojce pokazujo, ale słanje {{GENDER:$2|wužywarjeju|wužywarce}} njejo se raźiło: $1",
        "changeemail": "E-mailowu adresu změniś",
        "changeemail-header": "Kontowu e-mailowu adresu změniś",
        "changeemail-no-info": "Dejš pśizjawjony byś, aby direktny pśistup na toś ten bok měł.",
        "undo-nochange": "Zda se, až změna jo se južo anulěrowała.",
        "undo-summary": "Wersija $1 wót [[Special:Contributions/$2|$2]] ([[User talk:$2|Diskusija]]) jo se anulěrowała",
        "undo-summary-username-hidden": "Změna $1 schowanego wužywarja jo se anulěrowała",
-       "cantcreateaccounttitle": "Njejo móžno wužywarske konto wutwóriś",
        "cantcreateaccount-text": "Wutwórjenje wužywarskego konta z toś teje IP adresy ('''$1''') jo blokěrowane pśez [[User:$3|$3]].\n\nPśicyna, kótaruž $3 jo zapódał, jo ''$2''.",
        "cantcreateaccount-range-text": "Napóranje kontow z IP-adresow we wobcerku <strong>$1</strong>, kótaryž wopśimujo twóju IP-adresu (<strong>$4</strong>), jo se wót [[User:$3|$3]] zablokěrowało.\n\nPśicyna pódana wót $3 jo <em>$2</em>",
        "viewpagelogs": "Protokole boka pokazaś",
index 7558a77..fd75693 100644 (file)
        "parser-unstrip-loop-warning": "अनस्ट्रिप लुप धेखिन्छ",
        "parser-unstrip-recursion-limit": "अन्स्ट्रिप पुनरावर्तन सिमा पार गरियो ($1)",
        "converter-manual-rule-error": "म्यानुअल भाषा अनुवाद सिध्दान्तमी समस्या धेखियो",
-       "cantcreateaccounttitle": "खाता बनाउन सकिएन",
        "viewpagelogs": "यै पानाका लगहरू हेर",
        "nohistory": "ये पृष्ठका लागी कोइ सम्पादन इतिहास छैन।",
        "currentrev": "अहिलको पुनरावलोकन",
        "group-bureaucrat": "प्रशासकहरू",
        "group-suppress": "लुकौन्या वाला",
        "group-all": "(सबै)",
-       "group-user-member": "{{लिङग:$1|प्रयोगकर्ता}}",
-       "group-autoconfirmed-member": "{{लिङग:$1|स्वनिर्धारित प्रयोगकर्ता}}",
-       "group-bot-member": "{{लिङग:$1|बोट}}",
-       "group-sysop-member": "{{लिङग:$1|प्रबन्धक}}",
-       "group-bureaucrat-member": "{{लिङग:$1|प्रशासक}}",
-       "group-suppress-member": "{{लिङग:$1|दबाउन्या}}",
+       "group-user-member": "{{GENDER:$1|प्रयोगकर्ता}}",
+       "group-autoconfirmed-member": "{{GENDER:$1|स्वनिर्धारित प्रयोगकर्ता}}",
+       "group-bot-member": "{{GENDER:$1|बोट}}",
+       "group-sysop-member": "{{GENDER:$1|प्रबन्धक}}",
+       "group-bureaucrat-member": "{{GENDER:$1|प्रशासक}}",
+       "group-suppress-member": "{{GENDER:$1|दबाउन्या}}",
        "grouppage-user": "{{एनयस:आयोजना}}:प्रयोगकर्ताहरू",
        "grouppage-autoconfirmed": "{{एनयस:आयोजना}}:स्वनिर्धारित प्रयोगकर्ताहरू",
        "grouppage-bot": "{{एनयस:आयोजना}}:बोटहरु",
        "tooltip-t-whatlinkshere": "यो सित जोडियाका सब्बै विकि पानानको सूची",
        "tooltip-t-recentchangeslinked": "यै पानामी जोडियाका पानामी अहिलको परिवर्तन",
        "tooltip-feed-atom": "यै पानाकी लेखा एक एटम फिड",
-       "tooltip-t-contributions": "यिन प्रयोगकर्ताका योगदानहरूको सूची हेरपुई",
+       "tooltip-t-contributions": "{{GENDER:$1|यिन प्रयोगकर्ता}}का योगदानहरूको सूची हेरपुई",
        "tooltip-t-upload": "चित्र अप्लोड अर",
        "tooltip-t-specialpages": "सब्बै खास खास पानानको शुचि ।",
        "tooltip-t-print": "यो पानाको छापिन्या संस्करण",
index 4bfec97..12f6e28 100644 (file)
@@ -67,6 +67,7 @@
        "tog-watchdefault": "Προσθήκη σελίδων που επεξεργάζομαι στη λίστα παρακολούθησης.",
        "tog-watchmoves": "Προσθήκη σελίδων που μετακινώ στη λίστα παρακολούθησής μου",
        "tog-watchdeletion": "Προσθήκη σελίδων και αρχείων που διαγράφω στη λίστα παρακολούθησής μου",
+       "tog-watchuploads": "Να προσθέσετε νέα αρχεία που ανεβάσετε στη λίστα παρακολούθησής μου",
        "tog-watchrollback": "Προσθήκη σελίδων όπου έχω κάνει μια επαναφορά στη λίστα παρακολούθησής μου",
        "tog-minordefault": "Σήμανση εκ προεπιλογής όλων των αλλαγών ως μικρής κλίμακας",
        "tog-previewontop": "Εμφάνιση προεπισκόπησης πριν από το πλαίσιο επεξεργασίας",
        "tagline": "Από {{SITENAME}}",
        "help": "Βοήθεια",
        "search": "Αναζήτηση",
+       "search-ignored-headings": "#<!-- αφήστε αυτή τη γραμμή όπως είναι --> <pre>\n# Επικεφαλίδες που θα αγνοηθούν από την αναζήτηση.\n# Αλλαγές σε αυτό ισχύουν μόλις η σελίδα με τον τίτλο ευρετηριαστεί.\n# Μπορείτε να επιβάλετε επανευρετηρίαση της σελίδας κάνοντας μια κενή επεξεργασία.\n# Η σύνταξη είναι ως εξής:\n# * Όλα από ένα χαρακτήρα \"#\" μέχρι το τέλος της γραμμής είναι ένα σχόλιο.\n# * Κάθε μη κενή γραμμή είναι ο ακριβής τίτλος που θα αγνοήσει, κεφαλαία/πεζά και τα πάντα.\nΠαραπομπές\nΕξωτερικοί σύνδεσμοι\nΔείτε επίσης\n #</pre> <!-- leave this line exactly as it is -->",
        "searchbutton": "Αναζήτηση",
        "go": "Μετάβαση",
        "searcharticle": "Μετάβαση",
        "botpasswords-label-delete": "Διαγραφή",
        "botpasswords-label-resetpassword": "Επαναφορά κωδικού",
        "botpasswords-label-grants": "Ισχύουσες άδειες:",
+       "botpasswords-help-grants": "Κάθε παραχώρηση δίνει πρόσβαση στα ορισμένα δικαιώματα χρήστη που που ήδη έχει ένας λογαριασμός χρήστη. Δείτε τη [[Special:ListGrants|πίνακας παραχωρήσεων]] για περισσότερες πληροφορίες.",
        "botpasswords-label-restrictions": "Περιορισμοί χρήσης:",
        "botpasswords-label-grants-column": "Χορηγήθηκε",
        "botpasswords-bad-appid": "Η ονομασία του ρομπότ «$1» δεν είναι έγκυρη.",
+       "botpasswords-insert-failed": "Αποτυχία να προστεθεί το όνομα bot \"$1\". Έχει ήδη προστεθεί;",
        "botpasswords-update-failed": "Αποτυχία ενημέρωσης της ονομασίας του ρομπότ «$1». Μήπως διαγράφτηκε ο κωδικός;",
        "botpasswords-created-title": "Ο κωδικός πρόσβασης του ρομπότ δημιουργήθηκε",
-       "botpasswords-created-body": "Ο κωδικός πρόσβασης του ρομπότ «$1» δημιουργήθηκε επιτυχώς.",
+       "botpasswords-created-body": "Ο κωδικός πρόσβασης για το όνομα ρομπότ \"$1\" του χρήστη \"$2\" δημιουργήθηκε.",
        "botpasswords-updated-title": "Ο κωδικός πρόσβασης του ρομπότ ενημερώθηκε",
-       "botpasswords-updated-body": "Ο κωδικός πρόσβασης του ρομπότ «$1» ενημερώθηκε με επιτυχία.",
+       "botpasswords-updated-body": "Ο κωδικός πρόσβασης του ρομπότ «$1» του χρήστη «$2» ενημερώθηκε.",
        "botpasswords-deleted-title": "Ο κωδικός πρόσβασης του ρομπότ διαγράφτηκε",
+       "botpasswords-deleted-body": "Ο κωδικός πρόσβασης για το όνομα ρομπότ \"$1\" του χρήστη \"$2\" διαγράφηκε.",
+       "botpasswords-newpassword": "Ο νέος κωδικός πρόσβασης για να συνδεθείτε με το <strong>$1</strong> είναι <strong>$2</strong>. <em>Παρακαλούμε σημειώστε το για μελλοντική αναφορά.</em>",
        "botpasswords-no-provider": "BotPasswordsSessionProvider δεν είναι διαθέσιμο.",
+       "botpasswords-restriction-failed": "Περιορισμοί κωδικών πρόσβασης bot εμποδίζουν τη συγκεκριμένη σύνδεση.",
        "resetpass_forbidden": "Οι κωδικοί πρόσβασης δεν μπορούν να αλλαχθούν",
+       "resetpass_forbidden-reason": "Οι κωδικοί πρόσβασης δεν μπορούν να αλλαχθούν: $1",
        "resetpass-no-info": "Πρέπει να είστε συνδεδεμένος για να δείτε αυτήν την σελίδα απευθείας",
        "resetpass-submit-loggedin": "Αλλαγή κωδικού",
        "resetpass-submit-cancel": "Ακύρωση",
-       "resetpass-wrong-oldpass": "Λάθος προσωρινός ή κανονικός κωδικός.\nΜπορεί να έχετε ήδη αλλάξει επιτυχώς τον κωδικό σας ή να έχετε ζητήσει έναν νέο προσωρινό κωδικό.",
+       "resetpass-wrong-oldpass": "Λάθος προσωρινός ή κανονικός κωδικός.\nΜπορεί να έχετε ήδη αλλάξει τον κωδικό σας ή να έχετε ζητήσει έναν νέο προσωρινό κωδικό.",
        "resetpass-recycled": "Παρακαλούμε επαναφέρετε τον κωδικό πρόσβασής σας σε κάτι διαφορετικό από τον τρέχοντα κωδικό πρόσβασης.",
        "resetpass-temp-emailed": "Έχετε συνδεθεί με έναν προσωρινό κωδικό μέσω ηλεκτρονικού ταχυδρομείου.\nΓια να ολοκληρώσετε τη σύνδεση, πρέπει να ορίσετε έναν νέο κωδικό εδώ:",
        "resetpass-temp-password": "Προσωρινός κωδικός:",
        "passwordreset-emailelement": "Όνομα χρήστη: \n$1\n\nΠροσωρινός κωδικός πρόσβασης:\n$2",
        "passwordreset-emailsentemail": "Αν αυτή η διεύθυνση ηλεκτρονικού ταχυδρομείου συνδέεται με το  λογαριασμό σας, τότε  θα σας αποσταλεί μήνυμα ηλεκτρονικού ταχυδρομείου για την επαναφορά του κωδικού πρόσβασης.",
        "passwordreset-emailsentusername": "Αν υπάρχει μια διεύθυνση ηλεκτρονικού ταχυδρομείου που συνδέεται με αυτό το όνομα χρήστη, τότε θα σας αποσταλεί ένα μήνυμα ηλεκτρονικού ταχυδρομείου για την επαναφορά του κωδικού πρόσβασης.",
-       "passwordreset-emailsent-capture": "Έχει αποσταλεί email επαναφοράς κωδικού, το οποίο φαίνεται πιο κάτω.",
-       "passwordreset-emailerror-capture": "Ένα email επαναφοράς κωδικού έχει δημιουργηθεί, το οποίο φαίνεται πιο κάτω, αλλά απέτυχε η αποστολή του στο  {{GENDER:$2|χρήστη}}: $1",
+       "passwordreset-invalideamil": "Μη έγκυρη διεύθυνση ηλεκτρονικού ταχυδρομείου",
        "changeemail": "Αλλαγή ή αφαίρεση της διεύθυνσης ηλεκτρονικού ταχυδρομείου",
        "changeemail-header": "Συμπληρώστε αυτήν τη φόρμα για να αλλάξετε τη διεύθυνσή σας ηλεκτρονικού ταχυδρομείου. Αν θέλετε να καταργήσετε τη σύνδεση οποιασδήποτε διεύθυνσης ηλεκτρονικού ταχυδρομείου με το λογαριασμό σας, αφήστε τη νέα διεύθυνση ηλεκτρονικού ταχυδρομείου κενή κατά την υποβολή της φόρμας.",
-       "changeemail-passwordrequired": "Θα χρειαστεί να εισαγάγετε τον κωδικό σας για να επιβεβαιώσετε την αλλαγή αυτή.",
        "changeemail-no-info": "Πρέπει να έχετε συνδεθεί για άμεση πρόσβαση σε αυτήν τη σελίδα.",
        "changeemail-oldemail": "Τρέχουσα διεύθυνση ηλεκτρονικού ταχυδρομείου:",
        "changeemail-newemail": "Νέα διεύθυνση ηλεκτρονικού ταχυδρομείου:",
        "minoredit": "Αυτή είναι μια μικροαλλαγή",
        "watchthis": "Παρακολούθηση αυτής της σελίδας",
        "savearticle": "Αποθήκευση σελίδας",
+       "savechanges": "Αποθήκευση αλλαγών",
        "publishpage": "Δημοσίευση σελίδας",
        "publishchanges": "Δημοσίευση αλλαγών",
        "preview": "Προεπισκόπηση",
        "undo-nochange": "Η επεξεργασία φαίνεται να έχει ήδη αναιρεθεί.",
        "undo-summary": "Αναίρεση αναθεώρησης $1 υπό τον/την [[Special:Contribs/$2|$2]] ([[User talk:$2|Συζήτηση]])",
        "undo-summary-username-hidden": "Αναίρεση αναθεώρησης $1 από ένα κρυμμένο χρήστη",
-       "cantcreateaccounttitle": "Ο λογαριασμός δεν μπορεί να δημιουργηθεί",
        "cantcreateaccount-text": "Η δημιουργία λογαριασμού από αυτή τη διεύθυνση IP ('''$1''') έχει αποτραπεί από τον [[User:$3|$3]].\n\nΟ λόγος που δόθηκε από τον $3 είναι ''$2''",
        "cantcreateaccount-range-text": "Η δημιουργία λογαριασμού από διευθύνσεις IP στην περιοχή  <strong>$1</strong>, που περιλαμβάνει τη δική σας διεύθυνση IP (<strong>$4</strong>), έχει αποκλειστεί από τον [[User:$3|$3]].\n\nΗ αιτιολογία που δόθηκε από τον $3 είναι \"$2\"",
        "viewpagelogs": "Προβολή αρχείων καταγραφών για αυτήν τη σελίδα",
        "mergehistory-done": "$3 {{PLURAL:$3|έκδοση|εκδόσεις}} του $1 συγχωνεύθηκαν επιτυχώς στο [[:$2]].",
        "mergehistory-fail": "Αδύνατη η εκτέλεση της συγχώνευσης ιστορικού, παρακαλούμε κάντε επανέλεγχο των παραμέτρων σελίδας και χρόνου.",
        "mergehistory-fail-bad-timestamp": "Η χρονική σήμανση δεν είναι έγκυρη.",
+       "mergehistory-fail-invalid-source": "Η πηγή σελίδας δεν είναι έγκυρη.",
+       "mergehistory-fail-invalid-dest": "Η σελίδα προορισμού δεν είναι έγκυρη.",
        "mergehistory-fail-toobig": "Δεν είναι δυνατό να πραγματοποιηθεί η συγχώνευση ιστορικών, καθώς πάνω από $1 {{PLURAL:$1|αναθεώρηση|αναθεωρήσεις}} θα μετακινούνταν.",
        "mergehistory-no-source": "Η σελίδα πηγής $1 δεν υπάρχει.",
        "mergehistory-no-destination": "Η σελίδα προορισμού $1 δεν υπάρχει.",
        "grant-createeditmovepage": "Δημιουργία, επεξεργασία και μετακίνηση σελίδων",
        "grant-delete": "Διαγραφή σελίδων, αναθεωρήσεων, και αρχείων καταγραφής",
        "grant-editinterface": "Επεξεργασία του ονοματοχώρου Mediawiki και της CSS/JavaScript χρήστη",
+       "grant-editmycssjs": "Επεξεργαστείτε το δικό σας CSS/JavaScript",
        "grant-editmyoptions": "Επεξεργασία των προτιμήσεών χρήστη σας",
        "grant-editmywatchlist": "Επεξεργασία της λίστας παρακολούθησής σας",
        "grant-editpage": "Επεξεργασία υπαρχουσών σελίδων",
        "rightslogtext": "Καταγραφές των αλλαγών στα δικαιώματα χρηστών.",
        "action-read": "να διαβάσετε αυτή τη σελίδα",
        "action-edit": "τροποποιήσετε αυτή τη σελίδα",
-       "action-createpage": "να δημιουργήσετε σελίδες",
-       "action-createtalk": "να δημιουργήσετε σελίδες συζήτησης",
+       "action-createpage": "να δημιουργήσετε αυτή τη σελίδα",
+       "action-createtalk": "να δημιουργήσετε αυτή τη σελίδα συζήτησης",
        "action-createaccount": "να δημιουργήσετε αυτό το λογαριασμό χρήστη",
        "action-autocreateaccount": "Δημιουργείστε αυτόματα αυτόν τον εξωτερικό λογαριασμό χρήστη",
        "action-history": "προβολή ιστορικού αυτή της σελίδας",
        "action-viewmyprivateinfo": "προβάλετε τις προσωπικές σας πληροφορίες",
        "action-editmyprivateinfo": "επεξεργαστείτε τις προσωπικές σας πληροφορίες",
        "action-editcontentmodel": "επεξεργαστείτε το μοντέλο περιεχομένου σελίδας",
-       "action-managechangetags": "δημιοÏ\85Ï\81γία ÎºÎ±Î¹ Î´Î¹Î±Î³Ï\81αÏ\86ή ÎµÏ\84ικεÏ\84Ï\8eν από τη βάση δεδομένων",
+       "action-managechangetags": "δημιοÏ\85Ï\81γήÏ\83εÏ\84ε ÎºÎ±Î¹ Î´Î¹Î±Î³Ï\81άÏ\88εÏ\84ε ÎµÏ\84ικέÏ\84εÏ\82 από τη βάση δεδομένων",
        "action-applychangetags": "εφαρμογή ετικετών μαζί με τις αλλαγές σας",
        "action-changetags": "πρόσθεση και αφαίρεση αυθαίρετων ετικετών σε μεμονωμένες εκδόσεις και καταχωρήσεις καταγραφών",
+       "action-deletechangetags": "διαγράψετε ετικέτες από τη βάση δεδομένων",
        "nchanges": "$1 {{PLURAL:$1|αλλαγή|αλλαγές}}",
        "enhancedrc-since-last-visit": "$1 {{PLURAL:$1|από την τελευταία επίσκεψη}}",
        "enhancedrc-history": "ιστορικό",
        "log-edit-tags": "Επεξεργασία ετικετών των επιλεγμένων καταχωρήσεων του αρχείου καταγραφής",
        "checkbox-all": "Όλα",
        "checkbox-none": "Κανένα",
+       "checkbox-invert": "Αντιστροφή",
        "allpages": "Όλες οι σελίδες",
        "nextpage": "Επόμενη σελίδα ($1)",
        "prevpage": "Προηγούμενη σελίδα ($1)",
        "revertpage": "Ανάκληση των αλλαγών [[Special:Contributions/$2|$2]] ([[User talk:$2|συζήτηση]]) επιστροφή στην προηγούμενη αναθεώρηση [[User:$1|$1]]",
        "revertpage-nouser": "Αναστράφηκαν οι επεξεργασίες από τον (όνομα χρήστη αφαιρέθηκε) στη τελευταία έκδοση από τον/την {{GENDER:$1|[[User:$1|$1]]}}φ",
        "rollback-success": "Ανεστραμμένες εκδόσεις από $1, αλλάχθηκαν στην προηγούμενη έκδοση από $2.",
+       "rollback-success-notify": "Αναίρεση επεξεργασιών από $1; επιστροφή στην τελευταία αναθεώρηση από $2.[$3 Εμφάνιση αλλαγών]",
        "sessionfailure-title": "Η συνεδρία απέτυχε",
        "sessionfailure": "Υπάρχει πρόβλημα με τη σύνδεσή σας -η ενέργεια αυτή ακυρώθηκε προληπτικά για την αντιμετώπιση τυχόν πειρατείας συνόδου (session hijacking). Παρακαλoύμε πατήστε \"Επιστροφή\", ξαναφορτώστε τη σελίδα από την οποία φθάσατε εδώ και προσπαθήστε ξανά.",
        "changecontentmodel": "Αλλαγή μοντέλου περιεχομένου της σελίδας",
        "changecontentmodel-title-label": "Τίτλος σελίδας",
        "changecontentmodel-model-label": "Νέο μοντέλο περιεχομένου",
        "changecontentmodel-reason-label": "Αιτία:",
+       "changecontentmodel-submit": "Αλλαγή",
        "changecontentmodel-success-title": "Το περιεχόμενο πρότυπο άλλαξε",
        "changecontentmodel-success-text": "Ο τύπος περιεχομένου του [[:$1]] έχει αλλάξει.",
        "changecontentmodel-cannot-convert": "Το περιεχόμενο του [[:$1]] δεν μπορεί να μετατραπεί σε τύπο $2.",
        "ipb-unblock": "Τερμάτισε τη φραγή για ένα όνομα χρήστη ή μια διεύθυνση IP",
        "ipb-blocklist": "Δες τις υπάρχουσες φραγές",
        "ipb-blocklist-contribs": "Συνεισφορές {{GENDER:$1|του $1|της $1}}",
+       "ipb-blocklist-duration-left": "Απομένουν $1",
        "unblockip": "Άρση φραγής χρήστη",
        "unblockiptext": "Χρησιμοποιήστε την παρακάτω φόρμα για να αποκαταστήσετε την πρόσβαση σε επεξεργασία, σε μια διεύθυνση IP ή σε ένα χρήστη που είχε αποκλειστεί με φραγή.",
        "ipusubmit": "Άρση φραγής",
        "lockdbsuccesstext": "Η βάση δεδομένων έχει κλειδωθεί.<br />\nΘυμηθείτε να [[Special:UnlockDB|αφαιρέσετε το κλείδωμα]] αφότου η συντήρησή σας ολοκληρωθεί.",
        "unlockdbsuccesstext": "Η βάση δεδομένων έχει ξεκλειδωθεί.",
        "lockfilenotwritable": "Το αρχείο κλειδώματος της βάσης δεδομένων δεν είναι εγγράψιμο. Για να κλειδώσετε ή να ξεκλειδώσετε τη βάση δεδομένων, αυτό το αρχείο πρέπει να είναι εγγράψιμο από τον εξυπηρετητή web.",
+       "databaselocked": "Η βάση δεδομένων είναι είδη κλειδωμένη.",
        "databasenotlocked": "Η βάση δεδομένων δεν είναι κλειδωμένη.",
        "lockedbyandtime": "(Από {{GENDER:$1| $1 }} στις $2 στις $3 )",
        "move-page": "Μετακίνηση $1",
        "lastmodifiedatby": "Η σελίδα αυτή τροποποιήθηκε τελευταία φορά στις  $2, $1 από το χρήστη $3.",
        "othercontribs": "Βασισμένο στη δουλειά του/των $1",
        "others": "άλλοι",
-       "siteusers": "{{SITENAME}} {{PLURAL:$2|χρηστή|χρηστών}} του ιστοχώρου $1",
+       "siteusers": "{{SITENAME}} {{PLURAL:$2|χρηστής|χρήστες}} του ιστοχώρου $1",
        "anonusers": "{{PLURAL:$2|ανώνυμος χρήστης|ανώνυμοι χρήστες}} $1 του {{SITENAME}}",
        "creditspage": "Αναγνώριση συνεισφοράς στη σελίδα",
        "nocredits": "Δεν υπάρχουν πληροφορίες σχετικά με την αναγνώριση συνεισφοράς σε αυτή τη σελίδα.",
        "newimages-legend": "Φίλτρο",
        "newimages-label": "Όνομα αρχείου (ή μέρος αυτού):",
        "newimages-showbots": "Εμφάνιση αρχείων ανεβασμένων από ρομπότ",
+       "newimages-hidepatrolled": "Απόκρυψη ελεγμένων αρχείων.",
        "noimages": "Δεν υπάρχουν εικόνες.",
        "ilsubmit": "Αναζήτηση",
        "bydate": "ημερομηνίας",
        "confirm-watch-top": "Προσθήκη αυτής της σελίδας στη λίστα παρακολούθησης σας;",
        "confirm-unwatch-button": "Εντάξει",
        "confirm-unwatch-top": "Κατάργηση αυτής της σελίδας από τη λίστα παρακολούθησης σας;",
+       "confirm-rollback-button": "Εντάξει",
+       "confirm-rollback-top": "Επαναφέρετε τις επεξεργασίες σε αυτή τη σελίδα;",
        "quotation-marks": "«$1»",
        "imgmultipageprev": "← προηγούμενη σελίδα",
        "imgmultipagenext": "επόμενη σελίδα →",
        "tags-delete-not-found": "Η ετικέτα «$1» δεν υπάρχει.",
        "tags-delete-too-many-uses": "Η ετικέτα «$1» εφαρμόζεται σε πάνω από {{PLURAL:$2|μία αναθεώρηση|$2 αναθεωρήσεις}}, που σημαίνει ότι δεν μπορεί να διαγραφεί.",
        "tags-delete-warnings-after-delete": "Η ετικέτα «$1» διαγράφηκε με επιτυχία, αλλά {{PLURAL:$2|προέκυψε η ακόλουθη προειδοποίηση|προέκυψαν οι ακόλουθες προειδοποιήσεις}}:",
+       "tags-delete-no-permission": "Δεν έχετε άδεια να διαχειριστείτε ετικέτες αλλαγής.",
        "tags-activate-title": "Ενεργοποίηση ετικέτας",
        "tags-activate-question": "Πρόκειται να ενεργοποιήσετε την ετικέτα «$1».",
        "tags-activate-reason": "Αιτία:",
        "special-characters-group-ipa": "ΔΦΑ",
        "special-characters-group-symbols": "Σύμβολα",
        "special-characters-group-greek": "Ελληνικό",
+       "special-characters-group-greekextended": "Προέκταση του ελληνικού",
        "special-characters-group-cyrillic": "Κυριλλικό",
        "special-characters-group-arabic": "Αραβικό",
        "special-characters-group-arabicextended": "Arabic extended",
        "sessionprovider-mediawiki-session-cookiesessionprovider": "συνεδρίες με βάση τα cookies",
        "sessionprovider-nocookies": "Τα Cookies μπορούν να απενεργοποιηθούν. Βεβαιωθείτε ότι έχετε ενεργοποιημένα τα cookies και ξεκινήστε πάλι.",
        "randomrootpage": "Τυχαία κύρια σελίδα",
-       "log-action-filter-rights": "Πληκτρολογήστε για αλλαγή δικαιωμάτων:"
+       "log-action-filter-block": "Τύπος φραγής:",
+       "log-action-filter-rights": "Πληκτρολογήστε για αλλαγή δικαιωμάτων:",
+       "log-action-filter-all": "Όλα",
+       "log-action-filter-block-block": "Φραγή",
+       "log-action-filter-block-reblock": "Τροποποίηση φραγής",
+       "log-action-filter-block-unblock": "Άρση φραγής",
+       "log-action-filter-protect-protect": "Προστασία",
+       "log-action-filter-protect-modify": "Τροποποίηση προστασίας",
+       "log-action-filter-protect-unprotect": "Άρση προστασίας",
+       "log-action-filter-protect-move_prot": "Μετακίνηση προστασίας",
+       "log-action-filter-rights-rights": "Χειροκίνητη αλλαγή",
+       "log-action-filter-rights-autopromote": "Αυτόματη αλλαγή",
+       "authmanager-create-disabled": "Η δημιουργία λογαριασμού έχει απενεργοποιηθεί.",
+       "authmanager-realname-label": "Πραγματικό όνομα",
+       "authmanager-realname-help": "Πραγματικό όνομα του χρήστη",
+       "authmanager-provider-temporarypassword": "Προσωρινός κωδικός",
+       "authprovider-resetpass-skip-label": "Παράβλεψη",
+       "authprovider-resetpass-skip-help": "Παράβλεψη της επαναφοράς του κωδικού πρόσβασης.",
+       "specialpage-securitylevel-not-allowed-title": "Δεν επιτρέπεται",
+       "cannotauth-not-allowed-title": "Δεν έχετε δικαίωμα πρόσβασης.",
+       "cannotauth-not-allowed": "Δεν επιτρέπεται να χρησιμοποιήσετε αυτή τη σελίδα",
+       "credentialsform-account": "Όνομα λογαριασμού:",
+       "linkaccounts": "Σύνδεση λογαριασμών",
+       "linkaccounts-success-text": "Ο λογαριασμός συνδέθηκε",
+       "linkaccounts-submit": "Σύνδεση λογαριασμών"
 }
index e29d60c..e1c37c8 100644 (file)
        "passwordreset-emailelement": "Username:\n$1\n\nTemporary password:\n$2",
        "passwordreset-emailsentemail": "If this email address is associated with your account, then a password reset email will be sent.",
        "passwordreset-emailsentusername": "If there is an email address associated with this username, then a password reset email will be sent.",
-       "passwordreset-emailsent-capture": "A password reset email has been sent, which is shown below.",
-       "passwordreset-emailerror-capture": "A password reset email was generated, which is shown below, but sending it to the {{GENDER:$2|user}} failed: $1",
        "passwordreset-emailsent-capture2": "The password reset {{PLURAL:$1|email has|emails have}} been sent. The {{PLURAL:$1|username and password|list of usernames and passwords}} is shown below.",
        "passwordreset-emailerror-capture2": "Emailing the {{GENDER:$2|user}} failed: $1 The {{PLURAL:$3|username and password|list of usernames and passwords}} is shown below.",
        "passwordreset-nocaller": "A caller must be provided",
        "changeemail": "Change or remove email address",
        "changeemail-summary": "",
        "changeemail-header": "Complete this form to change your email address. If you would like to remove the association of any email address from your account, leave the new email address blank when submitting the form.",
-       "changeemail-passwordrequired": "You will need to enter your password to confirm this change.",
        "changeemail-no-info": "You must be logged in to access this page directly.",
        "changeemail-oldemail": "Current email address:",
        "changeemail-newemail": "New email address:",
        "undo-nochange": "The edit appears to have already been undone.",
        "undo-summary": "Undo revision $1 by [[Special:Contributions/$2|$2]] ([[User talk:$2|talk]])",
        "undo-summary-username-hidden": "Undo revision $1 by a hidden user",
-       "cantcreateaccounttitle": "Cannot create account",
        "cantcreateaccount-text": "Account creation from this IP address (<strong>$1</strong>) has been blocked by [[User:$3|$3]].\n\nThe reason given by $3 is <em>$2</em>",
        "cantcreateaccount-range-text": "Account creation from IP addresses in the range <strong>$1</strong>, which includes your IP address (<strong>$4</strong>), has been blocked by [[User:$3|$3]].\n\nThe reason given by $3 is <em>$2</em>",
        "createaccount-hook-aborted": "$1",
        "uploadstash-errclear": "Clearing the files failed.",
        "uploadstash-refresh": "Refresh the list of files",
        "uploadstash-thumbnail": "view thumbnail",
+       "uploadstash-exception": "Could not store upload in the stash ($1): \"$2\".",
        "invalid-chunk-offset": "Invalid chunk offset",
        "img-auth-accessdenied": "Access denied",
        "img-auth-nopathinfo": "Missing PATH_INFO.\nYour server is not set up to pass this information.\nIt may be CGI-based and cannot support img_auth.\nSee https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization.",
        "undeletehistorynoadmin": "This page has been deleted.\nThe reason for deletion is shown in the summary below, along with details of the users who had edited this page before deletion.\nThe actual text of these deleted revisions is only available to administrators.",
        "undelete-revision": "Deleted revision of $1 (as of $4, at $5) by $3:",
        "undeleterevision-missing": "Invalid or missing revision.\nYou may have a bad link, or the revision may have been restored or removed from the archive.",
+       "undeleterevision-duplicate-revid": "{{PLURAL:$1|One revision|$1 revisions}} could not be restored, because {{PLURAL:$1|its|their}} <code>rev_id</code> was already in use.",
        "undelete-nodiff": "No previous revision found.",
        "undeletebtn": "Restore",
        "undeletelink": "view/restore",
        "undeletedrevisions": "{{PLURAL:$1|1 revision|$1 revisions}} restored",
        "undeletedrevisions-files": "{{PLURAL:$1|1 revision|$1 revisions}} and {{PLURAL:$2|1 file|$2 files}} restored",
        "undeletedfiles": "{{PLURAL:$1|1 file|$1 files}} restored",
-       "cannotundelete": "Undelete failed:\n$1",
+       "cannotundelete": "Some or all of the undeletion failed:\n$1",
        "undeletedpage": "<strong>$1 has been restored</strong>\n\nConsult the [[Special:Log/delete|deletion log]] for a record of recent deletions and restorations.",
        "undelete-header": "See [[Special:Log/delete|the deletion log]] for recently deleted pages.",
        "undelete-search-title": "Search deleted pages",
        "sp-contributions-newbies-sub": "For new accounts",
        "sp-contributions-newbies-title": "User contributions for new accounts",
        "sp-contributions-blocklog": "block log",
-       "sp-contributions-suppresslog": "suppressed user contributions",
-       "sp-contributions-deleted": "deleted user contributions",
+       "sp-contributions-suppresslog": "suppressed {{GENDER:$1|user}} contributions",
+       "sp-contributions-deleted": "deleted {{GENDER:$1|user}} contributions",
        "sp-contributions-uploads": "uploads",
        "sp-contributions-logs": "logs",
        "sp-contributions-talk": "talk",
index e6a2368..323671c 100644 (file)
@@ -58,7 +58,7 @@
        "tog-extendwatchlist": "Etendi la atentaron por montri ĉiujn ŝanĝojn, ne nur la plej lastajn",
        "tog-usenewrc": "Grupigi ŝanĝojn laŭ paĝo en \"Lastaj ŝanĝoj\" kaj \"Atentaro\" (bezonas Ĝavaskripton)",
        "tog-numberheadings": "Aŭtomate numeri sekciojn",
-       "tog-showtoolbar": "Montri redakto-breton (per Ĝavaskripto)",
+       "tog-showtoolbar": "Montri redakto-breton",
        "tog-editondblclick": "Redakti paĝojn per duobla alklako",
        "tog-editsectiononrightclick": "Ŝalti sekcian redaktadon per dekstra musklako de sekciaj titoloj (per Ĝavaskripto)",
        "tog-watchcreations": "Aldoni miajn kreatajn paĝojn kaj miajn alŝutaĵojn al mia atentaro",
        "october-date": "$1‑a de oktobro",
        "november-date": "$1‑a de novembro",
        "december-date": "$1‑a de decembro",
-       "period-am": "ATM",
-       "period-pm": "PTM",
+       "period-am": "atm.",
+       "period-pm": "ptm.",
        "pagecategories": "{{PLURAL:$1|Kategorio|Kategorioj}}",
        "category_header": "Artikoloj en kategorio “$1”",
        "subcategories": "Subkategorioj",
        "updatedmarker": "ĝisdatigita de post mia lasta vizito",
        "printableversion": "Presebla versio",
        "permalink": "Konstanta ligilo",
-       "print": "Printi",
+       "print": "Presi",
        "view": "Vidi",
        "view-foreign": "Rigardi en $1",
        "edit": "Redakti",
        "cannotlogoutnow-text": "Ne eblas elsaluti dum uzado de $1.",
        "welcomeuser": "Bonvenon, $1!",
        "welcomecreation-msg": "Via konto estas kreita.\nNe forgesu ŝanĝi viajn [[Special:Preferences|{{SITENAME}}-preferojn]]",
-       "yourname": "Salutnomo:",
-       "userlogin-yourname": "Uzantonomo",
+       "yourname": "Uzantnomo:",
+       "userlogin-yourname": "Uzantnomo",
        "userlogin-yourname-ph": "Enigu vian uzantonomon",
        "createacct-another-username-ph": "Enigu la salutnomon:",
        "yourpassword": "Pasvorto:",
        "changepassword-success": "Via pasvorto estis ŝanĝita!",
        "changepassword-throttled": "Vi tro ofte provis ensaluti al ĉi tiu konto.\nBonvolu atendi $1 antaŭ ol reprovi.",
        "botpasswords": "Robotaj pasvortoj",
-       "botpasswords-summary": "<em>Robotaj pasvortoj</em> ebligas aliron al uzanto-konto per API sen uzado de ĉefaj ensalutaj datumoj de la konto. La uzanto-rajtoj disponeblaj dum ensaluto per robota pasvorto povas esti limigitaj.\n\nSe vi ne scias, kial vi devus fari tion, vi probable maldevus fari tion. Neniu devus peti vin generi pasvorton tie ĉi kaj transdoni ĝin al li.",
+       "botpasswords-summary": "<em>Robotaj pasvortoj</em> ebligas aliron al uzanto-konto per API sen uzado de ĉefaj ensalutaj datumoj de la konto. La uzantorajtoj disponeblaj dum ensaluto per robota pasvorto povas esti limigitaj.\n\nSe vi ne scias, kial vi devus fari tion, vi probable ne devus fari tion. Neniu devus peti vin generi pasvorton ĉi tie por transdoni.",
        "botpasswords-disabled": "Robotaj pasvortoj estas malŝaltitaj.",
        "botpasswords-no-central-id": "Por uzi robotajn pasvortojn vi devas esti ensalutita al centra konto.",
        "botpasswords-existing": "Ekzistantaj robotaj pasvortoj",
        "passwordreset-text-many": "{{PLURAL:$1|Plenumu unu el la kampoj por restarigi vian pasvorton.}}",
        "passwordreset-disabled": "Pasvortaj restarigoj estis malŝaltitaj en ĉi tiu vikio.",
        "passwordreset-emaildisabled": "Retpoŝtaj funkcioj estas malfunkciigitaj en tiu ĉi vikio.",
-       "passwordreset-username": "Salutnomo:",
+       "passwordreset-username": "Uzantnomo:",
        "passwordreset-domain": "Domajno:",
        "passwordreset-capture": "Vidi la rezultan retpoŝton?",
        "passwordreset-capture-help": "Se vi markis ĉi tiun skatoleton, la retpoŝto (kun provizora pasvorto) estos montrita al vi kaj estos sendita al la uzanto.",
        "passwordreset-emailelement": "Salutnomo: \n$1\n\nProvizora pasvorto: \n$2",
        "passwordreset-emailsentemail": "Se tiu ĉu retpoŝta adreso estas kunligita kun via konto, tiam al ĉi tiu adreso estos sendita retpoŝto por renovigi pasvorton.",
        "passwordreset-emailsentusername": "Se estas retpoŝta adreso, kiu estas asociita kun tiu uzantnomo, tiam ni sendos retpoŝtan mesaĝon pri reagordado de la pasvorto.",
-       "passwordreset-emailsent-capture": "Retpoŝto kun renovigita pasvorto estis sendita, kiu estas montrata malsupre.",
-       "passwordreset-emailerror-capture": "Retpoŝto kun renovigita pasvorto estis generita, montrata sube, sed sendado al la {{GENDER:$2|uzanto}} malsukcesis: $1",
        "passwordreset-emailsent-capture2": "La {{PLURAL:$1|retpoŝto|retpoŝtojn}} de pasvorta reensignado estis sendita. La {{PLURAL:$1|salutnomo kaj pasvorto|listo de salutnomoj kaj pasvortoj}} estas vidigita sube.",
-       "passwordreset-emailerror-capture2": "Retpoŝtado al la {{GENDER:$2|uzantiĉo|uzantino|uzanto}} malsukcesis: $1 La {{PLURAL:$3|salutnomo kaj pasvorta|listo de salutnomoj kaj pasvortoj}} estas vidigita sube.",
+       "passwordreset-emailerror-capture2": "Retpoŝtado al la {{GENDER:$2|uzanto}} malsukcesis: $1 La {{PLURAL:$3|uzantnomo kaj pasvorto|listo de uzantnomoj kaj pasvortoj}} estas vidigita malsupre.",
        "passwordreset-nocaller": "Vokanto devas esti provizita",
        "passwordreset-nosuchcaller": "Vokanto ne ekzistas: $1",
        "passwordreset-ignored": "La pasvorta reensignado ne estis pritraktita. Eble neniu provizanto estis formita?",
        "passwordreset-nodata": "Nek salutnomo nek retpoŝta adreso estis provizita",
        "changeemail": "Ŝanĝi aŭ forigi retpoŝtadreson",
        "changeemail-header": "Plenigu ĉi tiun formularon por ŝanĝi vian retpoŝtadreson. Se vi volas forigi la difinon de retpoŝtadreso por via uzantokonto, lasu la kampon por la nova retpoŝtadreso malplena ĉe la transigo.",
-       "changeemail-passwordrequired": "Vi devas entajpi vian pasvorton, por konfirmi ĉi tiun ŝanĝon.",
        "changeemail-no-info": "Vi devas ensaluti por atingi ĉi tiun paĝon rekte.",
        "changeemail-oldemail": "Aktuala retpoŝtadreso:",
        "changeemail-newemail": "Nova retpoŝtadreso:",
        "savearticle": "Konservi paĝon",
        "savechanges": "Konservi ŝanĝojn",
        "publishpage": "Publikigi paĝon",
+       "publishchanges": "Eldoni ŝanĝojn",
        "preview": "Antaŭrigardo",
        "showpreview": "Antaŭrigardo",
        "showdiff": "Montri ŝanĝojn",
        "accmailtext": "Hazarde generita pasvorto por [[User talk:$1|$1]] estis sendita al $2.\n\nLa pasvorto por ĉi tiu nova konto povas esti ŝanĝita en la paĝo ''[[Special:ChangePassword|ŝanĝi pasvorton]]'' dum ensalutado.",
        "newarticle": "(Nova)",
        "newarticletext": "Vi sekvis ligilon al paĝo ankoraŭ ne ekzistanta. Se vi volas krei ĝin, ektajpu malsupre (vidu la [$1 helpopaĝon] por klarigoj.) Se vi malintence alvenis ĉi tien, simple alklaku la retrobutonon de via retumilo.",
-       "anontalkpagetext": "<em>Jen diskutopaĝo por anonima kontribuanto kiu ne jam kreis konton aŭ ne uzas ĝin.</em>\nNi tial devas uzi la cifran IP-adreson por identigi lin/ŝin.\nĈi tia IP-adreso povas esti uzata de pluraj uzantoj.\nSe vi estas anonimulo kaj preferus eviti tiajn mistrafajn komentojn al vi, bonvolu [[Special:CreateAccount|krei konton]] aŭ [[Special:UserLogin|ensaluti]] por eviti estontan konfuzon pro aliaj anonimaj uzantoj.''",
+       "anontalkpagetext": "<em>Jen diskutopaĝo por anonima kontribuanto kiu ankoraŭ ne kreis konton aŭ ne uzas ĝin.</em>\nNi tial devas uzi la cifran IP-adreson por identigi tiun kontribuanton.\nĈi tia IP-adreso povas esti uzata de pluraj uzantoj.\nSe vi estas anonimulo kaj preferus eviti tiajn mistrafajn komentojn al vi, bonvolu [[Special:CreateAccount|krei konton]] aŭ [[Special:UserLogin|ensaluti]] por eviti estontan konfuzon pro aliaj anonimaj uzantoj.''",
        "noarticletext": "Mankas teksto en ĉi tiu paĝo.\nVi povas [[Special:Search/{{PAGENAME}}|serĉi ĉi tiun paĝtitolon]] en aliaj paĝoj,\n<span class=\"plainlinks\">[{{fullurl:{{#Special:Log}}|page={{FULLPAGENAMEE}}}} serĉi la rilatajn protokolojn],\naŭ [{{fullurl:{{FULLPAGENAME}}|action=edit}} krei ĉi tiun paĝon]</span>.",
        "noarticletext-nopermission": "Estas neniom da teksto en ĉi tiu paĝo.\nVi povas [[Special:Search/{{PAGENAME}}|serĉi ĉi tiun paĝan titolon]] en aliaj paĝoj,\naŭ <span class=\"plainlinks\">[{{fullurl:{{#Special:Log}}|page={{FULLPAGENAMEE}}}} serĉi la rilatajn protokolojn]</span>, sed vi ne rajtas krei ĉi tiun paĝon.",
        "missing-revision": "La revizio n-ro $1 de la paĝo nomata \"{{FULLPAGENAME}}\" ne ekzistas.\n\nTio kutime estas kaŭzata per sekvado de malaktuala historio-ligilo al paĝo forigita.\nDetaloj troveblos en la [{{fullurl:{{#Special:Log}}/delete|page={{FULLPAGENAMEE}}}} registro de forigoj].",
        "content-model-css": "CSS",
        "content-json-empty-object": "Malplena objeto",
        "content-json-empty-array": "Malplena tabelo",
-       "deprecated-self-close-category": "Paĝoj, kiuj enhavas nevalidan memferman HTML‑etikedon",
+       "deprecated-self-close-category": "Paĝoj kun nevalida memferma HTML‑etikedon",
        "duplicate-args-warning": "'''Averto:''' [[:$1]] vokas al [[:$2]] kun pli ol unu valoro por la parametro \"$3\". Nur la lasta liverita valoro estos uzata.",
        "duplicate-args-category": "Paĝoj kun pluroblaj argumentoj en ŝablonvokoj",
        "duplicate-args-category-desc": "La paĝo enhavas uzon de ŝablono kun pluroble uzitaj argumentoj, kiel ekzemple <code><nowiki>{{foo|bar=1|bar=2}}</nowiki></code> aŭ <code><nowiki>{{foo|bar|1=baz}}</nowiki></code>.",
        "undo-norev": "La redakto ne povis esti malfarita ĉar ĝi aŭ ne ekzistas aŭ estis forigita.",
        "undo-nochange": "Ŝajne la redakto jam estis malfarita.",
        "undo-summary": "Nuligis version $1 de [[Special:Contributions/$2|$2]] ([[User talk:$2|Diskuto]] | [[Special:Contributions/$2|{{MediaWiki:Contribslink}}]])",
-       "undo-summary-username-hidden": "Malfari ŝanĝon $1 de kaŝita uzulo",
-       "cantcreateaccounttitle": "Ne eblas krei konton",
+       "undo-summary-username-hidden": "Malfari ŝanĝon $1 de kaŝita uzanto",
        "cantcreateaccount-text": "Konto-kreado de ĉi tiu IP-adreso ('''$1''') estis forbarita de [[User:$3|$3]].\n\nLa kialo donata de $3 estas ''$2''.",
        "cantcreateaccount-range-text": "La kreado de kontoj de IP-adresoj en la intervalo <strong>$1</strong>, kiu inkludas vian IP-adreson (<strong>$4</strong>), estis blokita de [[User:$3|$3]].\n\nLa donita kialo de $3 estas <em>$2</em>",
-       "viewpagelogs": "Vidi la protokolojn por tiu ĉi paĝo",
+       "viewpagelogs": "Vidi la protokolojn por ĉi tiu paĝo",
        "nohistory": "Ne ekzistas historio de redaktoj por ĉi tiu paĝo.",
        "currentrev": "Aktuala versio",
        "currentrev-asof": "Nuna versio ekde $1",
        "prefs-reset-intro": "Vi povas uzi ĉi tiun paĝon por restarigi viajn agordojn al la originalaj defaŭltoj.\nĈi tiel ne estus malfarebla.",
        "prefs-emailconfirm-label": "Retpoŝta konfirmado:",
        "youremail": "Retadreso:",
-       "username": "{{GENDER:$1|Salutnomo}}:",
+       "username": "{{GENDER:$1|Uzantnomo}}:",
        "prefs-memberingroups": "{{GENDER:$2|Ano}} de {{PLURAL:$1|grupo|grupoj}}:",
        "prefs-registration": "Tempo de registrado:",
        "yourrealname": "Vera nomo:",
        "prefs-help-signature": "Komentoj en diskuto-paĝoj estu subskribita kun \"<nowiki>~~~~</nowiki>\" kiu estos konvertita al via subskribo kaj tempindiko.",
        "badsig": "Via kaŝnomo (por subskriboj) malvalidas. Bv. kontroli la HTML-etikedojn!",
        "badsiglength": "La subskribo estas tro longa.\nĜi devas esti sub $1 {{PLURAL:$1|signo|signoj}}.",
-       "yourgender": "Sekso:",
-       "gender-unknown": "Menciate vin, la programaro uzos vortojn de neŭtra genro, ĉiam kiam estos ebla",
-       "gender-male": "Vira",
-       "gender-female": "Ina",
+       "yourgender": "Kiel vi preferas esti priskribata?",
+       "gender-unknown": "Menciate vin, la programaro uzos seksneŭtrajn vortojn ĉiam kiam eblas",
+       "gender-male": "Li redaktas vikipaĝojn",
+       "gender-female": "Ŝi redaktas vikipaĝojn",
        "prefs-help-gender": "Nedeviga: uzita por sekseca salutado de la programaro. Ĉi tiu informo montriĝos publike.",
        "email": "Retadreso",
        "prefs-help-realname": "* Vera nomo estas nedeviga.\nSe vi elektas sciigi ĝin, ĝi estos uzita por aŭtorigi vin por viaj kontribuoj.",
        "userrights-lookup-user": "Administri grupojn de uzantoj",
        "userrights-user-editname": "Entajpu salutnomon:",
        "editusergroup": "Redakti grupojn de {{GENDER:$1|uzanto}}",
-       "editinguser": "Ŝanĝado de uzanto-rajtoj de la {{GENDER:$1|uzanto|uzantino}} <strong>[[User:$1|$1]]</strong> $2",
+       "editinguser": "Ŝanĝado de uzantorajtoj de la {{GENDER:$1|uzanto}} <strong>[[User:$1|$1]]</strong> $2",
        "userrights-editusergroup": "Redakti grupojn de uzantoj",
-       "saveusergroups": "Konservi grupojn de {{GENDER:$1|viruzuloj|uzulinoj|uzantoj}}",
+       "saveusergroups": "Konservi grupojn de {{GENDER:$1|uzantoj}}",
        "userrights-groupsmember": "Membro de:",
        "userrights-groupsmember-auto": "Implica membro de:",
        "userrights-groups-help": "Vi povas modifi la grupojn kiun ĉi uzanto enestas.\n* Markita markbutono signifas ke la uzanto estas en tiu grupo.\n* Nemarkita markbutono signifas ke la uzanto ne estas in tiu grupo.\n* Steleto (*) signifas ke vi ne povas forigi la grupon post vi aldonis ĝin, aŭ male.",
        "group-bureaucrat": "Burokratoj",
        "group-suppress": "Foriganaro",
        "group-all": "(ĉiuj)",
-       "group-user-member": "{{GENDER:$1|uzanto|uzantino}}",
-       "group-autoconfirmed-member": "{{GENDER:$1|aŭtomate konfirmita uzanto|aŭtomate konfirmita uzantino}}",
+       "group-user-member": "{{GENDER:$1|uzanto}}",
+       "group-autoconfirmed-member": "{{GENDER:$1|aŭtomate konfirmita uzanto}}",
        "group-bot-member": "{{GENDER:$1|roboto}}",
-       "group-sysop-member": "{{GENDER:$1|Administranto|Administrantino}}",
-       "group-bureaucrat-member": "{{GENDER:$1|Burokrato|Burokratino}}",
-       "group-suppress-member": "{{GENDER:$1|Superrigardanto|Superrigardantino}}",
+       "group-sysop-member": "{{GENDER:$1|administranto}}",
+       "group-bureaucrat-member": "{{GENDER:$1|burokrato}}",
+       "group-suppress-member": "{{GENDER:$1|superrigardanto}}",
        "grouppage-user": "{{ns:project}}:Uzantoj",
        "grouppage-autoconfirmed": "{{ns:project}}:Aŭtomate konfirmitaj uzantoj",
        "grouppage-bot": "{{ns:project}}:Robotoj",
        "usercreated": "{{GENDER:$3|Kreita}} je $1, $2",
        "newpages": "Novaj paĝoj",
        "newpages-submit": "Montri",
-       "newpages-username": "Salutnomo:",
+       "newpages-username": "Uzantnomo:",
        "ancientpages": "Plej malnovaj artikoloj",
        "move": "Alinomi",
        "movethispage": "Alinomi ĉi tiun paĝon",
        "emailuser": "Retpoŝti ĉi tiun uzanton",
        "emailuser-title-target": "Retpoŝti ĉi tiun {{GENDER:$1|uzanton}}",
        "emailuser-title-notarget": "Retpoŝti uzanton",
-       "emailpagetext": "Vi povas uzi la jenan paĝon por sendi retpoŝtan mesaĝon al ĉi tiu {{GENDER:$1|uzanto|uzantino}}.\nLa retadreso kiun vi enigis en [[Special:Preferences|viaj preferoj]] aperos kiel la \"De\" adreso de la retpoŝto, do la ricevonto eblos respondi rekte al vi.",
+       "emailpagetext": "Vi povas uzi la jenan paĝon por sendi retpoŝtan mesaĝon al ĉi tiu {{GENDER:$1|uzanto}}.\nLa retadreso kiun vi enigis en [[Special:Preferences|viaj preferoj]] aperos kiel la \"De\" adreso de la retpoŝto, do la ricevonto eblos respondi rekte al vi.",
        "defemailsubject": "{{SITENAME}} retmesaĝo de uzanto \"$1\"",
        "usermaildisabled": "Retpoŝto de uzantoj estas malŝaltita",
        "usermaildisabledtext": "Vi ne povas sendi retpoŝton al aliaj uzantoj en ĉi tiu vikio",
        "nowikiemailtext": "Ĉi tiu uzanto elektis ne ricevi retpoŝton de aliaj uzantoj.",
        "emailnotarget": "Neekzistanta aŭ malvalida salutnomo por ricevanto.",
        "emailtarget": "Enigi salutnomon de ricevonto",
-       "emailusername": "Salutnomo:",
+       "emailusername": "Uzantnomo:",
        "emailusernamesubmit": "Enigi",
        "email-legend": "Sendi retpoŝton al alia {{SITENAME}}-uzanto",
        "emailfrom": "De:",
        "namespace_association": "Asociita nomspaco",
        "tooltip-namespace_association": "Marku ĉi tiu skatolo por inkluzivi la diskutan aŭ teman nomspacon asocie de la elekta nomspaco",
        "blanknamespace": "(Ĉefa)",
-       "contributions": "Kontribuoj de {{GENDER:$1|uzanto|uzantino}}",
+       "contributions": "Kontribuoj de {{GENDER:$1|uzanto}}",
        "contributions-title": "Kontribuoj de uzanto $1",
        "mycontris": "Kontribuoj",
        "anoncontribs": "Kontribuoj",
        "ipboptions": "2 horoj:2 hours,1 tago:1 day,3 tagoj:3 days,1 semajno:1 week,2 semajnoj:2 weeks,1 monato:1 month,3 monatoj:3 months,6 monatoj:6 months,1 jaro:1 year,porĉiam:infinite",
        "ipbhidename": "Kaŝi salutnomon de redaktoj kaj listoj",
        "ipbwatchuser": "Atenti la paĝojn por uzanto kaj diskuto de ĉi tiu uzanto.",
-       "ipb-disableusertalk": "Preventi ĉi tiun uzanton redakti sian diskuto-paĝon, dum li estas forbarita",
+       "ipb-disableusertalk": "Preventi ĉi tiun uzanton redakti sian diskutpaĝon, dum ĝi estas forbarata",
        "ipb-change-block": "Reforbari la uzanton kun ĉi tiuj preferoj",
        "ipb-confirm": "Konfirmi forbaron",
        "badipaddress": "Neniu uzanto, aŭ la IP-adreso estas misformita.",
        "tooltip-pt-logout": "Elsaluti",
        "tooltip-pt-createaccount": "Ni rekomendas al vi kreon de uzantokonto kaj ensaluto; tamen, tio ne estas deviga",
        "tooltip-ca-talk": "Diskuto pri la artikolo",
-       "tooltip-ca-edit": "Redakti tiun ĉi paĝon",
+       "tooltip-ca-edit": "Redakti ĉi tiun paĝon",
        "tooltip-ca-addsection": "Starti novan sekcion",
        "tooltip-ca-viewsource": "Tiu paĝo estas protektita. Vi povas nur rigardi ties fonton.",
-       "tooltip-ca-history": "Antaŭaj versioj de tiu ĉi paĝo.",
+       "tooltip-ca-history": "Antaŭaj versioj de ĉi tiu paĝo.",
        "tooltip-ca-protect": "Protekti tiun ĉi paĝon",
        "tooltip-ca-unprotect": "Ŝanĝi protektadon de ĉi tiu paĝo",
        "tooltip-ca-delete": "Forigi tiun ĉi paĝon",
        "tooltip-ca-undelete": "Restarigu la redaktojn faritajn al tiu ĉi paĝo antaŭ ties forigo",
-       "tooltip-ca-move": "Alinomigi tiun ĉi paĝon",
-       "tooltip-ca-watch": "Aldoni tiun ĉi paĝon al via atentaro",
+       "tooltip-ca-move": "Alinomigi ĉi tiun paĝon",
+       "tooltip-ca-watch": "Aldoni ĉi tiun paĝon al via atentaro",
        "tooltip-ca-unwatch": "Forigi tiun ĉi paĝon el via atentaro",
        "tooltip-search": "Serĉi tra {{SITENAME}}",
        "tooltip-search-go": "Iru al paĝo kun ĉi preciza nomo se ĝi ekzistas",
        "tooltip-n-randompage": "Iri al hazarda paĝo",
        "tooltip-n-help": "La loko por eltrovi",
        "tooltip-t-whatlinkshere": "Listo de ĉiuj vikiaj paĝoj kiuj ligas ĉi tien",
-       "tooltip-t-recentchangeslinked": "Lastaj ŝanĝoj en paĝoj kiuj ligas al tiu ĉi paĝo",
+       "tooltip-t-recentchangeslinked": "Lastaj ŝanĝoj en paĝoj kiuj ligas al ĉi tiu paĝo",
        "tooltip-feed-rss": "RSS-fonto por tiu ĉi paĝo",
        "tooltip-feed-atom": "Atom-fonto por ĉi tiu paĝo",
        "tooltip-t-contributions": "Listo de kontribuoj de {{GENDER:$1|ĉi tiu uzanto}}",
-       "tooltip-t-emailuser": "Sendi retmesaĝon al {{GENDER:$1|tiu ĉi uzantiĉo|tiu ĉi uzantino|tiu ĉi uzanto}}",
+       "tooltip-t-emailuser": "Sendi retmesaĝon al {{GENDER:$1|ĉi tiu uzanto}}",
        "tooltip-t-info": "Pli da informo pri ĉi tiu paĝo",
        "tooltip-t-upload": "Alŝuti dosierojn",
        "tooltip-t-specialpages": "Listo de ĉiuj specialaj paĝoj",
        "lastmodifiedatby": "Ĉi paĝo estis laste ŝanĝita je $2, $1 de $3.",
        "othercontribs": "Bazita sur la laboro de $1.",
        "others": "aliaj",
-       "siteusers": "{{GENDER:$2|uzantiĉo|uzantino|uzanto}}{{PLURAL:$2||j}} $1 de {{SITENAME}}",
+       "siteusers": "{{PLURAL:$2|{{GENDER:$1|uzanto}}|uzantoj}} $1 de {{SITENAME}}",
        "anonusers": "{{SITENAME}}-{{PLURAL:$2|anonimulo|anonimuloj}} $1",
        "creditspage": "Atribuoj de paĝo",
        "nocredits": "Ne estas informo pri atribuoj por ĉi paĝo.",
        "revdelete-uname-unhid": "salutnomo malkaŝita",
        "revdelete-restricted": "aplikis limojn al administrantoj",
        "revdelete-unrestricted": "forigis limojn por administrantoj",
-       "logentry-block-block": "$1 {{GENDER:$2|forbaris}} la {{GENDER:$4|uzanton|uzantinon}} $3 por daŭro de $5 $6",
-       "logentry-block-unblock": "$1 {{GENDER:$2|malforbaris}} la {{GENDER:$4|uzanton|uzantinon}} $3",
-       "logentry-block-reblock": "$1 {{GENDER:$2|ŝanĝis}} agordojn de forbaro por la {{GENDER:$4|uzanto|uzantino}} $3 por daŭro de $5 $6",
-       "logentry-suppress-block": "$1 {{GENDER:$2|forbaris}} la {{GENDER:$4|uzanton|uzantinon}} $3 por daŭro de $5 $6",
-       "logentry-suppress-reblock": "$1 {{GENDER:$2|ŝanĝis}} agordojn de forbaro por la {{GENDER:$4|uzanto|uzantino}} $3 por daŭro de $5 $6",
+       "logentry-block-block": "$1 {{GENDER:$2|forbaris}} la {{GENDER:$4|uzanton $3}} por daŭro de $5 $6",
+       "logentry-block-unblock": "$1 {{GENDER:$2|malforbaris}} la {{GENDER:$4|uzanton $3}}",
+       "logentry-block-reblock": "$1 {{GENDER:$2|ŝanĝis}} agordojn de forbaro por la {{GENDER:$4|uzanto $3}} por daŭro de $5 $6",
+       "logentry-suppress-block": "$1 {{GENDER:$2|forbaris}} la {{GENDER:$4|uzanton $3}} por daŭro de $5 $6",
+       "logentry-suppress-reblock": "$1 {{GENDER:$2|ŝanĝis}} agordojn de forbaro por la {{GENDER:$4|uzanto $3}} por daŭro de $5 $6",
        "logentry-import-upload": "$1 {{GENDER:$2|importis}} $3 per dosiera alŝuto",
        "logentry-import-upload-details": "$1 {{GENDER:$2|importis}} $3 kiel dosiera alŝuto ($4 {{PLURAL:$4|revizio|revizioj}})",
        "logentry-import-interwiki": "$1 {{GENDER:$2|importis}} $3 de alia vikio",
index a9facb7..c4f01aa 100644 (file)
        "passwordreset-emailelement": "Nombre de {{GENDER:$1|usuario|usuaria}}: \n$1\n\nContraseña temporal: \n$2",
        "passwordreset-emailsentemail": "Si esta dirección de correo electrónico está asociada a tu cuenta, entonces se enviará un correo electrónico para restablecer la contraseña.",
        "passwordreset-emailsentusername": "Si existe una dirección de correo electrónico asociada a este nombre de usuario, entonces se enviará un correo para restablecer la contraseña.",
-       "passwordreset-emailsent-capture": "Se ha enviado un correo para el restablecimiento de la contraseña, el cual se muestra a continuación.",
-       "passwordreset-emailerror-capture": "Se ha generado un correo electrónico de restablecimiento de contraseña, que se muestra a continuación, pero ha fallado el envío {{GENDER:$2|al usuario|a la usuaria}}: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|El e-mail de restablecimiento de contraseña ha sido enviado|Los e-mails de restablecimiento de contraseña han sido enviados}}. {{PLURAL:$1|El nombre de usuario y la contraseña se muestra a continuación|La lista de nombres de usuarios y contraseñas se muestra a continuación}}.",
        "passwordreset-emailerror-capture2": "No fue posible mandar un correo electrónico {{Gender:$2|al usuario|a la usuaria}}: $1 {{PLURAL:$3|El nombre de usuario y la contraseña|La lista de nombres de usuarios y contraseñas}} se muestra a continuación.",
        "passwordreset-nocaller": "Debe de proporcionarse un interlocutor",
        "passwordreset-nodata": "No se ha proporcionado ni un nombre de usuario ni una dirección de correo electrónico",
        "changeemail": "Cambiar o eliminar la dirección de correo electrónico",
        "changeemail-header": "Completa este formulario para cambiar tu dirección de correo electrónico. Si quieres eliminar la asociación de cualquier dirección de correo electrónico con tu cuenta, deja en blanco la nueva dirección de correo electrónico cuando envíes el formulario.",
-       "changeemail-passwordrequired": "Tendrás que escribir tu contraseña para confirmar este cambio.",
        "changeemail-no-info": "Debes iniciar sesión para acceder directamente a esta página.",
        "changeemail-oldemail": "Dirección de correo electrónico actual:",
        "changeemail-newemail": "Dirección de correo electrónico nueva:",
        "undo-nochange": "Parece que ya se había deshecho la edición.",
        "undo-summary": "Se ha deshecho la revisión $1 de [[Special:Contributions/$2|$2]] ([[User talk:$2|disc.]])",
        "undo-summary-username-hidden": "Se ha deshecho la revisión $1 de un usuario oculto",
-       "cantcreateaccounttitle": "No se puede crear la cuenta",
        "cantcreateaccount-text": "[[User:$3|$3]] ha bloqueado la creación de cuentas desde esta dirección IP (<strong>$1</strong>).\n\nEl motivo dado por $3 es <em>$2</em>",
        "cantcreateaccount-range-text": "[[User:$3|$3]] ha bloqueado la creación de cuentas de usuario desde direcciones IP en el rango <strong>$1</strong>, en el que se encuentra tu dirección IP (<strong>$4</strong>).\n\nEl motivo dado por $3 es <em>$2</em>",
        "viewpagelogs": "Ver los registros de esta página",
        "noindex-category-desc": "La página contiene la palabra mágica <code><nowiki>__NOINDEX__</nowiki></code> (y está en un espacio de nombres donde la función está activada); y por ello los robots no la indizan.",
        "index-category-desc": "La página contiene la palabra mágica <code><nowiki>__INDEX__</nowiki></code> (y está en un espacio de nombres donde la función está activada); y por ello los robots la indizarán.",
        "post-expand-template-inclusion-category-desc": "Después de expandir todas las plantillas, el tamaño de la página es más grande que <code>$wgMaxArticleSize</code>, así que algunas plantillas no se expandieron.",
-       "post-expand-template-argument-category-desc": "Después de expandir un argumento de plantilla (algunos en tres llaves, como <code>{{{Foo}}})</code>, la página es más grande que <code>$wgMaxArticleSize</code>.",
+       "post-expand-template-argument-category-desc": "Después de expandir un argumento de plantilla (cualquier cosa encerrada en tres llaves, como <code>{{{Foo}}}</code>), la página es más grande que <code>$wgMaxArticleSize</code>.",
        "expensive-parserfunction-category-desc": "La página usa demasiadas funciones sintácticas costosas (como <code>#ifexist</code>). Consulta [https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:$wgExpensiveParserFunctionLimit Manual:$wgExpensiveParserFunctionLimit].",
        "broken-file-category-desc": "La página contiene un enlace roto a archivos (un enlace para incrustar un archivo cuando el archivo no existe).",
        "hidden-category-category-desc": "La categoría contiene <code><nowiki>__HIDDENCAT__</nowiki></code> en su página de contenido, lo que evita que aparezca en el cuadro de enlaces de categorías en las páginas, de forma predeterminada.",
        "watchnologin": "No has iniciado sesión",
        "addwatch": "Añadir a la lista de seguimiento",
        "addedwatchtext": "Se han añadido «[[:$1]]» y su página de discusión a tu [[Special:Watchlist|lista de seguimiento]].",
+       "addedwatchtext-talk": "Se han añadido «[[:$1]]» y su página asociada a tu [[Special:Watchlist|lista de seguimiento]].",
        "addedwatchtext-short": "La página \"$1\" ha sido añadida a tu lista de seguimiento.",
        "removewatch": "Quitar de la lista de seguimiento",
        "removedwatchtext": "Se han eliminado «[[:$1]]» y su página de discusión de tu [[Special:Watchlist|lista de seguimiento]].",
+       "removedwatchtext-talk": "Se han eliminado «[[:$1]]» y su página asociada de tu [[Special:Watchlist|lista de seguimiento]].",
        "removedwatchtext-short": "La página \"$1\" ha sido eliminada de tu lista de seguimiento.",
        "watch": "Vigilar",
        "watchthispage": "Vigilar esta página",
        "blocklist-timestamp": "Fecha y hora",
        "blocklist-target": "Destino",
        "blocklist-expiry": "Caduca",
-       "blocklist-by": "Administrador que bloqueó",
+       "blocklist-by": "Administrador que realizó el bloqueo",
        "blocklist-params": "Parámetros de bloqueo",
        "blocklist-reason": "Motivo",
        "ipblocklist-submit": "Buscar",
index 1b5d5e7..3b4e14f 100644 (file)
@@ -27,7 +27,8 @@
                        "Postituvi",
                        "Purodha",
                        "Macofe",
-                       "Adeliine"
+                       "Adeliine",
+                       "Metsavend"
                ]
        },
        "tog-underline": "Linkide allakriipsutus:",
        "passwordreset-emailelement": "Kasutajanimi: \n$1\n\nAjutine parool: \n$2",
        "passwordreset-emailsentemail": "Kui oled sidunud konto selle e-posti aadressiga, siis saadetakse sulle parooli lähtestamise e-kiri.",
        "passwordreset-emailsentusername": "Parooli lähtestamise e-kiri saadetakse, kui olemas on kontoga seotud e-posti aadress.",
-       "passwordreset-emailsent-capture": "E-kirjatsi on saadetud allpool näidatav parooli lähtestuskiri.",
-       "passwordreset-emailerror-capture": "Koostati allpool näidatav parooli lähtestuskiri, aga selle e-kirjatsi {{GENDER:$2|kasutajale}} saatmine ebaõnnestus: $1",
        "changeemail": "E-posti aadressi muutmine või eemaldamine",
        "changeemail-header": "Täida see vorm, et muuta oma e-posti aadress. Kui soovid, et konto poleks enam seotud ühegi e-posti aadressiga, siis jäta vormi esitamisel e-posti aadressi väli tühjaks.",
-       "changeemail-passwordrequired": "Et muudatus kinnitada, pead sisestama oma parooli.",
        "changeemail-no-info": "Otselingi kaudu sellele lehele jõudmiseks pead olema sisse loginud.",
        "changeemail-oldemail": "Praegune e-posti aadress:",
        "changeemail-newemail": "Uus e-posti aadress:",
        "minoredit": "See on pisiparandus",
        "watchthis": "Jälgi seda lehekülge",
        "savearticle": "Salvesta",
+       "publishpage": "Avalda lehekülg",
+       "publishchanges": "Avalda muudatused",
        "preview": "Eelvaade",
        "showpreview": "Näita eelvaadet",
        "showdiff": "Näita muudatusi",
        "undo-nochange": "Paistab, et see muudatus on juba eemaldatud.",
        "undo-summary": "Eemaldatud muudatus $1, mille tegi [[Special:Contributions/$2|$2]] ([[User talk:$2|arutelu]])",
        "undo-summary-username-hidden": "Eemaldatud redaktsioon $1, mille tegi peidetud kasutaja",
-       "cantcreateaccounttitle": "Ei saa kontot luua",
        "cantcreateaccount-text": "[[User:$3|$3]] on blokeerinud konto loomise sellelt IP-aadressilt (<strong>$1</strong>).\n\n$3 märkis järgmise põhjuse: <em>$2</em>",
        "cantcreateaccount-range-text": "Kontode loomine IP-aadressidelt vahemikus <strong>$1</strong>, millesse jääb sinu IP-aadress (<strong>$4</strong>), on blokeeritud. Blokeeris kasutaja [[User:$3|$3]].\n\n$3 tõi järgmise põhjuse: <em>$2</em>",
        "viewpagelogs": "Vaata selle lehekülje logisissekandeid",
        "tooltip-ca-nstab-category": "Näita kategooria lehte",
        "tooltip-minoredit": "Märgi see pisiparanduseks",
        "tooltip-save": "Salvesta muudatused",
+       "tooltip-publish": "Avalda oma muudatused",
        "tooltip-preview": "Näita tehtavaid muudatusi. Palun kasutage seda enne salvestamist!",
        "tooltip-diff": "Näita tehtavaid muudatusi.",
        "tooltip-compareselectedversions": "Näita erinevusi selle lehe kahe valitud versiooni vahel.",
index a6108cd..a79df94 100644 (file)
@@ -66,7 +66,7 @@
        "tog-ccmeonemails": "Beste erabiltzaileei bidaltzen dizkiedan mezuen kopiak niri ere bidali",
        "tog-diffonly": "''Diff''-ak agertzen direnean, orrialdearen edukiera ezkutatu",
        "tog-showhiddencats": "Ikusi kategoria ezkutuak",
-       "tog-norollbackdiff": "Rollback bat egin ondoren ezberdintasunak ez hartu aintzat",
+       "tog-norollbackdiff": "Rollback bat egin ondoren ezberdintasunak ez erakutsi",
        "tog-useeditwarning": "Abisa nazazu gorde gabeko aldaketak eginez orrialde bat uzten dudanean",
        "tog-prefershttps": "Erabili beti konexio seguru bat sartzerakoan",
        "underline-always": "Beti",
        "passwordreset-emailtitle": "{{SITENAME}}-rako kontuaren xehetasunak",
        "passwordreset-emailelement": "Erabiltzaile izena: \n$1\n\nBehin-behineko pasahitza: \n$2",
        "passwordreset-emailsentemail": "Hau zure konturako erregistratuta dagoen helbide elektronikoa baldin bada, mezu elektronikoa bidaliko da zure pasahitza berrezartzeko.",
-       "passwordreset-emailsent-capture": "Pasahitza berrezartzeko e-posta bat bidali dizugu, behean erakusten dena.",
        "changeemail": "Aldatu edo kendu e-mail helbidea",
        "changeemail-header": "Bete ezazu inprimaki hau, zure helbide elektronikoa aldatzeko. Zure kontuari helbide elektronikorik elkartuta ez izatea nahi baduzu, utz ezazu hutsik helbide elektroniko berria, inprimakia bidaltzen duzunean.",
        "changeemail-no-info": "Orrialde honetara zuzenean sartzeko izena eman behar duzu.",
        "undo-failure": "Ezin izan da aldaketa desegin tarteko aldaketekin gatazkak direla-eta.",
        "undo-norev": "Aldaketa ezin da desegin ez delako existitzen edo ezabatu zutelako.",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|eztabaida]]) wikilariaren $1 berrikuspena desegin da",
-       "cantcreateaccounttitle": "Ezin izan da kontua sortu",
        "cantcreateaccount-text": "IP helbide honetatik ('''$1''') kontu berria sortzeko aukera blokeatu du [[User:$3|$3]](e)k.\n\n$3(e)k emandako arrazoia: ''$2''",
        "viewpagelogs": "Orrialde honen erregistroak ikusi",
        "nohistory": "Orrialde honek ez dauka aldaketa historiarik.",
        "mergehistory-go": "Aldaketa bateragarriak erakutsi",
        "mergehistory-submit": "Berrikuspenak bateratu",
        "mergehistory-empty": "Ezin da berrikuspenik bateratu",
-       "mergehistory-done": "$1(e)ko {{PLURAL:$3|berrikuspen|berrikuspen}} bateratu egin {{PLURAL:$3|da|dira}} [[:$2]](e)n.",
+       "mergehistory-done": "$1(e)ko {{PLURAL:$3|berrikuspen}} bateratu egin {{PLURAL:$3|da|dira}} [[:$2]](e)n.",
        "mergehistory-fail": "Ezin izan da historia bateratu; egiaztatu orrialde eta denbora parametroak.",
        "mergehistory-no-source": "Ez da $1 jatorrizko orrialdea existitzen.",
        "mergehistory-no-destination": "Ez da $1 helburu orrialdea existitzen.",
        "emailccsubject": "Zure mezuaren kopia $1(r)i: $2",
        "emailsent": "Mezua bidali egin da",
        "emailsenttext": "Zure e-posta mezua bidali egin da.",
-       "emailuserfooter": "E-posta hau $1(e)k bidali dio $2(r)i {{SITENAME}}ko \"{{int:emailuser}}\" funtzioa erabiliz.",
+       "emailuserfooter": "E-posta hau $1(e)k {{GENDER:$1|bidali}} dio {{GENDER:$2|$2}}(r)i {{SITENAME}}ko \"{{int:emailuser}}\" funtzioa erabiliz.",
        "usermessage-summary": "Sistema mezua uzten.",
        "usermessage-editor": "Sistemako mezularia",
        "watchlist": "Jarraipen zerrenda",
index 739dd08..cd16fd1 100644 (file)
        "passwordreset-emailelement": "نام کاربری: \n$1\n\nگذرواژهٔ موقت: \n$2",
        "passwordreset-emailsentemail": "اگر نشانی پست الکترونیکی که وارد کردید برای حساب کاربریتان ثبت شده باشد، یک نامهٔ بازنشانی گذرواژه به آن فرستاده می‌شود.",
        "passwordreset-emailsentusername": "اگر نشانی پست الکترونیکی مرتبطی موجود باشد، یک نامه برای بازنشانی گذرواژه به آن ارسال خواهد شد.",
-       "passwordreset-emailsent-capture": "یک ایمیل بازنشانی که در پایین نمایش داده شده، فرستاده شده است.",
-       "passwordreset-emailerror-capture": "ایمیل بازنشانی، که در زیر نمایش داده شده، ایجاد شد، ولی ارسال آن به {{GENDER:$2|کاربر}} موفقیت‌آمیز نبود: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|نامهٔ|نامهٔ}} بازنشانی گذرواژه ارسال شد. در زير $1 نام کاربری و گذرواژه در حال نمایش است.",
        "passwordreset-emailerror-capture2": "ارسال ناموفق نامه به $2: $1\nدر زير $3 نام کاربری و گذرواژه در حال نمایش است",
        "passwordreset-nocaller": "فراخواننده می‌بايست مشخص شده باشد",
        "passwordreset-nodata": "یک نام کاربری و یا یک آدرس ايميل، هيچکدام ارائه نشده",
        "changeemail": "تغییر یا حذف نشانی ایمیل",
        "changeemail-header": "برای تغییر ایمیلتان این فرم را کامل کنید. برای حذف ایملیتان کافی است بخش ایمیل را خالی رها کنید و فرم را ارسال کنید.",
-       "changeemail-passwordrequired": "برای تائید این تغییر باید گذرواژه‌تان را وارد کنید.",
        "changeemail-no-info": "برای دسترسی مستقیم به این صفحه شما باید به سامانه وارد شده باشید.",
        "changeemail-oldemail": "آدرس ایمیل کنونی:",
        "changeemail-newemail": "آدرس ایمیل جدید:",
        "watchthis": "پی‌گیری این صفحه",
        "savearticle": "صفحه ذخیره شود",
        "savechanges": "ذخیرهٔ تغییرات",
-       "publishpage": "اÙ\86تشار صفحه",
-       "publishchanges": "اÙ\86تشار تغییرات",
+       "publishpage": "ذخÛ\8cرÙ\87 صفحه",
+       "publishchanges": "ذخÛ\8cرÙ\87 تغییرات",
        "preview": "پیش‌نمایش",
        "showpreview": "پیش‌نمایش",
        "showdiff": "نمایش تغییرات",
        "undo-nochange": "به نظر می‌رسد ویرایش از پیش واگردانی شده است.",
        "undo-summary": "خنثی‌سازی ویرایش $1 توسط [[Special:Contributions/$2|$2]] ([[User talk:$2|بحث]])",
        "undo-summary-username-hidden": "خنثی‌سازی نسخهٔ $1 به دست یک کاربر پنهان‌شده",
-       "cantcreateaccounttitle": "نمی‌توان حساب باز کرد",
        "cantcreateaccount-text": "امكان ساختن حساب کاربری از این این نشانی آی‌پی ('''$1''') توسط [[User:$3|$3]] سلب شده است.\n\nدلیل ارائه شده توسط $3 چنین است: $2",
        "cantcreateaccount-range-text": "ایجاد حساب از آدرس آی‌پی در مجموعه‌ی <strong>$1</strong>، که شامل آدرس آی‌پی شما (<strong>$4</strong>) است، توسط [[User:$3|$3]] متوقف شده‌است.\nدلیل ارائه شده توسط $3، $2 است.",
        "viewpagelogs": "نمایش سیاهه‌های این صفحه",
        "notvisiblerev": "آخرین نسخه توسط کاربری دیگر حذف شده‌است",
        "watchlist-details": "بدون احتساب صفحه‌های جداگانهٔ بحث، {{PLURAL:$1|$1 صفحه|$1 صفحه}} در فهرست پی‌گیری‌های شما قرار {{PLURAL:$1|دارد|دارند}}.",
        "wlheader-enotif": "ایمیل‌های اعلان فعال است.",
-       "wlheader-showupdated": "صفحه‌هایی که پس از آخرین بازدید شما تغییر کرده‌اند '''پررنگ''' نمایش داده شده‌اند.",
+       "wlheader-showupdated": "صفحه‌هایی که پس از آخرین بازدید شما تغییر کرده‌اند <strong>پررنگ</strong> نمایش داده شده‌اند.",
        "wlnote": "در زیر {{PLURAL:$1|تغییری|<strong>$1</strong> تغییری}} که در {{PLURAL:$2|ساعت|<strong>$2</strong> ساعت}} گذشته انجام شده موجود است، تاریخ آخرین بازیابی: $3، $4",
        "wlshowlast": "نمایش آخرین $1 ساعت $2 روز",
        "watchlist-hide": "نهفتن",
index dda086c..74de0d5 100644 (file)
        "passwordreset-emailelement": "Käyttäjätunnus: \n$1\n\nVäliaikainen salasana: \n$2",
        "passwordreset-emailsentemail": "Jos tämä on sinun tunnuksellesi rekisteröity sähköpostiosoite, salasanan uudistamisesta kertova viesti lähetetään.",
        "passwordreset-emailsentusername": "Jos on olemassa vastaava rekisteröity sähköpostiosoite, salasanan uudistamisesta kertova viesti lähetetään.",
-       "passwordreset-emailsent-capture": "Salasanan uudistamisesta kertova sähköpostiviesti on lähetetty, ja se näkyy myös alla.",
-       "passwordreset-emailerror-capture": "Allaoleva sähköpostiviesti luotiin, mutta sen lähettäminen {{GENDER:$2|käyttäjälle}} epäonnistui: $1",
        "passwordreset-emailsent-capture2": "Salasananpalautus{{PLURAL:$1|sähköposti|sähköpostit}} on lähetetty. {{PLURAL:$1|Käyttäjä ja salasana|Luettelo käyttäjistä ja salasanoista}} näytetään alapuolella.",
        "passwordreset-emailerror-capture2": "Sähköpostin lähettäminen {{GENDER:$2|käyttäjälle}} epäonnistui: $1 {{PLURAL:$3|Käyttäjänimi ja salasana|Luettelo käyttäjänimistä ja salasanoista}} näytetään alla.",
        "passwordreset-invalideamil": "Virheellinen sähköpostiosoite",
        "passwordreset-nodata": "Käyttäjätunnusta ja salasanaa ei annettu",
        "changeemail": "Muuta tai poista sähköpostiosoite",
        "changeemail-header": "Täydennä tämä lomake, jolla voit muuttaa sähköpostiosoitettasi. Jos haluat poistaa sähköpostiosoitteesi kokonaan tunnuksesi yhteydestä, älä kirjoita uudeksi osoitteeksi mitään vaan jätä se tyhjäksi.",
-       "changeemail-passwordrequired": "Sinun on syötettävä salasanasi vahvistaaksesi tämän muutoksen.",
        "changeemail-no-info": "Tämän sivun käyttö edellyttää sisäänkirjautumista.",
        "changeemail-oldemail": "Nykyinen sähköpostiosoite:",
        "changeemail-newemail": "Uusi sähköpostiosoite:",
        "undo-nochange": "Tämä muokkaus näyttää olevan jo kumottu.",
        "undo-summary": "Kumottu muokkaus $1, jonka teki [[Special:Contributions/$2|$2]] ([[User talk:$2|keskustelu]])",
        "undo-summary-username-hidden": "Kumottu muokkaus $1, jonka on tehnyt piilotettu käyttäjä",
-       "cantcreateaccounttitle": "Tunnusta ei voida luoda",
        "cantcreateaccount-text": "Tunnusten luonti tästä IP-osoitteesta ('''$1''') on estetty. Estäjänä on [[User:$3|$3]].\n\nKäyttäjän $3 antama syy on ''$2''",
        "cantcreateaccount-range-text": "Tunnusten luominen IP-osoitteista osoitealueella <strong>$1</strong>, johon kuuluu myös sinun käyttämäsi IP-osoite (<strong>$4</strong>), on estetty. Eston on asettanut [[User:$3|$3]].\n\nSyy estolle on \"$2\".",
        "viewpagelogs": "Näytä tämän sivun lokit",
index cd4f7e2..cfdb0bb 100644 (file)
        "passwordreset-emailelement": "Nom d’utilisateur : \n$1\n\nMot de passe temporaire : \n$2",
        "passwordreset-emailsentemail": "Si cette adresse de courriel est associée à votre compte, alors un courriel de réinitialisation de mot de passe sera envoyé.",
        "passwordreset-emailsentusername": "S’il y a une adresse de courriel associée à ce nom d’utilisateur, alors un courriel de réinitialisation de mot de passe sera envoyé.",
-       "passwordreset-emailsent-capture": "Un courriel de réinitialisation de mot de passe a été envoyé, qui est affiché ci-dessous.",
-       "passwordreset-emailerror-capture": "Un courriel de réinitialisation de mot de passe a été généré, qui est affiché ci-dessous, mais l’envoi à l’{{GENDER:$2|utilisateur|utilisatrice}} a échoué : $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|Le courriel de réinitialisation du mot de passe a été envoyé|Les courriels de réinitialisation du mot de passe ont été envoyés}}. {{PLURAL:$1|Le nom d’utilisateur et le mot de passe sont affichés|La liste des noms d’utilisateur et mots de passe est affichée}} ci-dessous.",
        "passwordreset-emailerror-capture2": "L’envoi de courriel à {{GENDER:$2|l’utilisateur|l’utilisatrice}} a échoué : $1 {{PLURAL:$3|Le nom d’utilisateur et le mot de passe sont affichés|La liste des noms d’utilisateur et des mots de passe est affichée}} ci-dessous.",
        "passwordreset-nocaller": "Un appelant doit être fourni",
        "passwordreset-nosuchcaller": "L’appelant n’existe pas : $1",
        "passwordreset-ignored": "La réinitialisation du mot de passe n’a pas été gérée. Peut-être qu’aucun fournisseur n’a été configuré ?",
        "passwordreset-invalideamil": "Adresse de messagerie non valide",
-       "passwordreset-nodata": "Ni un nom d’utilisateur ni une adresse de messagerie n’a  été fourni",
+       "passwordreset-nodata": "Aucun nom d’utilisateur ou adresse de messagerie n’a été fourni",
        "changeemail": "Changer ou supprimer l’adresse de courriel",
        "changeemail-header": "Complétez ce formulaire pour modifier votre adresse de courriel. Si vous voulez supprimer l’association d’une adresse de courriel avec votre compte, laissez la nouvelle adresse de courriel vide lors de la soumission du formulaire.",
-       "changeemail-passwordrequired": "Vous devrez saisir votre mot de passe pour confirmer cette modification.",
        "changeemail-no-info": "Vous devez être connecté pour pouvoir accéder directement à cette page.",
        "changeemail-oldemail": "Adresse de courriel actuelle :",
        "changeemail-newemail": "Nouvelle adresse de courriel :",
        "undo-nochange": "Il semblerait que la modification ait déjà été annulée.",
        "undo-summary": "Annulation des modifications $1 de [[Special:Contributions/$2|$2]] ([[User talk:$2|discussion]])",
        "undo-summary-username-hidden": "Annuler la révision $1 par un utilisateur masqué",
-       "cantcreateaccounttitle": "Vous ne pouvez pas créer de compte.",
        "cantcreateaccount-text": "La création de compte depuis cette adresse IP (<strong>$1</strong>) a été bloquée par [[User:$3|$3]]. \n\nLa raison donnée par $3 était : <em>$2</em>",
        "cantcreateaccount-range-text": "La création de compte depuis les adresses IP de la plage <strong>$1</strong>, où se trouve votre adresse IP (<strong>$4</strong>), a été bloquée par [[User:$3|$3]].\n\nLe motif fourni par $3 est <em>$2</em>",
        "viewpagelogs": "Voir les opérations sur cette page",
        "recentchangeslinked-feed": "Suivi des pages liées",
        "recentchangeslinked-toolbox": "Suivi des pages liées",
        "recentchangeslinked-title": "Suivi des pages associées à « $1 »",
-       "recentchangeslinked-summary": "Ceci est une liste des modifications faites récemment sur des pages liées à une page spécifique (ou à des membres d'une catégorie spécifique). \nLes pages de [[Special:Watchlist|votre liste de suivi]] sont <strong>en gras</strong>.",
+       "recentchangeslinked-summary": "Voici les modifications faites récemment sur des pages liées depuis une page spécifique ou vers des membres d'une catégorie spécifique. \nLes pages de [[Special:Watchlist|votre liste de suivi]] sont <strong>en gras</strong>.",
        "recentchangeslinked-page": "Nom de la page :",
        "recentchangeslinked-to": "Afficher les modifications des pages qui comportent un lien vers la page donnée plutôt que l'inverse",
        "recentchanges-page-added-to-category": "[[:$1]] ajouté à la catégorie",
        "uploadnologin": "Non connecté",
        "uploadnologintext": "Vous devez vous $1 pour importer des fichiers.",
        "upload_directory_missing": "Le répertoire d’import de fichier ($1) est introuvable et n’a pas pu être créé par le serveur web.",
-       "upload_directory_read_only": "Le répertoire d’import de fichier ($1) n’est pas accessible en écriture par le serveur web.",
+       "upload_directory_read_only": "Le serveur web n’a pas accès en écriture au répertoire d’import de fichier ($1).",
        "uploaderror": "Erreur lors de l’import",
        "upload-recreate-warning": "'''Attention : Un fichier portant ce nom a été supprimé ou déplacé.'''\n\nLe journal des suppressions et celui des déplacements de cette page sont affichés ici pour informations :",
        "uploadtext": "Utilisez ce formulaire pour importer des fichiers sur le serveur.\nPour voir ou rechercher des images précédemment envoyées, consultez la [[Special:FileList|liste des images]]. L’import est aussi enregistré dans le [[Special:Log/upload|journal d’import des fichiers]], et les suppressions dans le [[Special:Log/delete|journal des suppressions]].\n\nPour inclure un fichier dans une page, utilisez un lien de la forme :\n* '''<code><nowiki>[[</nowiki>{{ns:file}}<nowiki>:fichier.jpg]]</nowiki></code>''', pour afficher le fichier en pleine résolution (dans le cas d’une image) ;\n* '''<code><nowiki>[[</nowiki>{{ns:file}}<nowiki>:fichier.png|200px|thumb|left|texte descriptif]]</nowiki></code>''' pour utiliser une miniature de 200 pixels de large dans une boîte à gauche avec « texte descriptif » comme description ;\n* '''<code><nowiki>[[</nowiki>{{ns:media}}<nowiki>:fichier.ogg]]</nowiki></code>''' pour lier directement vers le fichier sans l’afficher.",
        "upload-preferred": "{{PLURAL:$2|Format|Formats}} de fichiers {{PLURAL:$2|préféré|préférés}} : $1.",
        "upload-prohibited": "‎{{PLURAL:$2|Format|Formats}} de fichiers {{PLURAL:$2|interdit|interdits}} : $1.",
        "uploadlogpage": "Journal d’import de fichiers",
-       "uploadlogpagetext": "Voici la liste des derniers fichiers importés sur le serveur.\nVoyez la [[Special:NewFiles|galerie des nouveaux fichiers]] pour une représentation plus visuelle.",
+       "uploadlogpagetext": "Voici les derniers fichiers téléversés.\nVoyez la [[Special:NewFiles|galerie des nouveaux fichiers]] pour une représentation plus visuelle.",
        "filename": "Nom du fichier",
        "filedesc": "Description",
        "fileuploadsummary": "Description :",
        "filesource": "Source :",
        "ignorewarning": "Ignorer l'avertissement et sauvegarder le fichier quand même",
        "ignorewarnings": "Ignorer tous les avertissements",
-       "minlength1": "Le noms de fichiers doivent comprendre au moins une lettre.",
-       "illegalfilename": "Le nom de fichier « $1 » contient des caractères interdits dans les titres de pages. Merci de le renommer et de l'importer à nouveau.",
-       "filename-toolong": "Le nom du fichier ne peut pas dépasser 240 octets.",
+       "minlength1": "Les noms de fichiers doivent comprendre au moins une lettre.",
+       "illegalfilename": "Le nom de fichier « $1 » contient des caractères interdits dans les titres de pages. \nMerci de le renommer et de l'importer à nouveau.",
+       "filename-toolong": "Les noms de fichier ne peuvent pas dépasser 240 octets.",
        "badfilename": "Le fichier a été renommé en « $1 ».",
        "filetype-mime-mismatch": "L'extension du fichier « .$1 » ne correspond pas au type MIME détecté du fichier ($2).",
-       "filetype-badmime": "Les fichiers du type MIME « $1 » ne peuvent pas être importés.",
+       "filetype-badmime": "Les fichiers de type MIME « $1 » ne peuvent pas être importés.",
        "filetype-bad-ie-mime": "Le fichier ne peut pas être importé parce qu'il serait détecté comme « $1 » par Internet Explorer, ce qui correspond à un type de fichier interdit car potentiellement dangereux.",
-       "filetype-unwanted-type": "'''« .$1 »''' est un format de fichier non désiré.\n{{PLURAL:$3|Le type de fichier préconisé est|Les types de fichiers préconisés sont}} $2.",
-       "filetype-banned-type": "''' « .$1 » '''{{PLURAL:$4|n'est pas un type de fichier autorisé|ne sont pas des types de fichiers autorisés}}. \n{{PLURAL:$3|le type de fichier autorisé est |les types de fichiers autorisés sont}} $2.",
+       "filetype-unwanted-type": "<strong>« .$1 »</strong> est un format de fichier non désiré.\n{{PLURAL:$3|Le type de fichier préconisé est|Les types de fichiers préconisés sont}} $2.",
+       "filetype-banned-type": "<strong>« .$1 »</strong>{{PLURAL:$4|n'est pas un type de fichier autorisé|ne sont pas des types de fichiers autorisés}}. \n{{PLURAL:$3|Le type de fichier autorisé est |Les types de fichiers autorisés sont}} $2.",
        "filetype-missing": "Le fichier n'a aucune extension (comme « .jpg » par exemple).",
        "empty-file": "Le fichier que vous avez soumis était vide.",
        "file-too-large": "Le fichier que vous avez soumis était trop grand.",
        "tmp-create-error": "Impossible de créer le fichier temporaire.",
        "tmp-write-error": "Erreur d'écriture du fichier temporaire.",
        "large-file": "Les fichiers importés ne devraient pas dépasser $1 ; ce fichier fait $2.",
-       "largefileserver": "La taille de ce fichier est supérieure au maximum autorisé.",
+       "largefileserver": "La taille de ce fichier est supérieure au maximum autorisé par le serveur.",
        "emptyfile": "Le fichier que vous voulez importer semble vide.\nCeci peut être dû à une erreur dans le nom du fichier.\nVeuillez vérifier que vous désirez vraiment importer ce fichier.",
        "windows-nonascii-filename": "Ce wiki ne supporte pas les noms de fichiers avec des caractères spéciaux.",
        "fileexists": "Un fichier existe déjà sous ce nom.\nMerci de vérifier <strong>[[:$1]]</strong> si vous n'êtes pas certain{{GENDER:||e|}} de vouloir le remplacer.\n[[$1|thumb]]",
-       "filepageexists": "La page de description pour ce fichier a déjà été créée ici <strong>[[:$1]]</strong>, mais aucun fichier n'existe actuellement sous ce nom.\nLe résumé que vous allez spécifier n'apparaîtra pas sur la page de description.\nPour que ce soit le cas, vous devrez modifier manuellement la page. [[$1|thumb]]",
+       "filepageexists": "La page de description pour ce fichier a déjà été créée ici <strong>[[:$1]]</strong>, mais aucun fichier n'existe actuellement sous ce nom.\nLe résumé que vous allez spécifier n'apparaîtra pas sur la page de description.\nPour que ce soit le cas, vous devrez modifier manuellement la page. \n[[$1|thumb]]",
        "fileexists-extension": "Un fichier existe avec un nom proche : [[$2|thumb]]\n* Nom du fichier à importer : <strong>[[:$1]]</strong>\n* Nom du fichier existant : <strong>[[:$2]]</strong>\nPeut-être voulez-vous utiliser un nom plus explicite ?",
-       "fileexists-thumbnail-yes": "Le fichier semble être une image en taille réduite ''(vignette)''. [[$1|thumb]]\nVeuillez vérifier le fichier <strong>[[:$1]]</strong>.\nSi le fichier vérifié est la même image avec la taille initiale, il n'y a pas besoin d'importer une version réduite.",
-       "file-thumbnail-no": "Le nom du fichier commence par <strong>$1</strong>.\nIl est possible qu'il s'agisse d'une version réduite ''(vignette)''.\nSi vous disposez du fichier en haute résolution, importez-le, sinon veuillez modifier son nom.",
-       "fileexists-forbidden": "Un fichier avec ce nom existe déjà et ne peut pas être écrasé.\nSi vous voulez toujours importer votre fichier, veuillez revenir en arrière et utiliser un autre nom. [[File:$1|thumb|center|$1]]",
-       "fileexists-shared-forbidden": "Un fichier portant ce nom existe déjà dans le dépôt de fichiers partagé.\nSi vous voulez toujours importer votre fichier, veuillez revenir en arrière et utiliser un autre nom. [[File:$1|thumb|center|$1]]",
+       "fileexists-thumbnail-yes": "Le fichier semble être une image en taille réduite <em>(vignette)</em>. \n[[$1|thumb]]\nVeuillez vérifier le fichier <strong>[[:$1]]</strong>.\nSi le fichier vérifié est la même image avec la taille initiale, il n'y a pas besoin d'importer une version réduite.",
+       "file-thumbnail-no": "Le nom du fichier commence par <strong>$1</strong>.\nIl est possible qu'il s'agisse d'une version réduite <em>(vignette)</em>.\nSi vous disposez du fichier en haute résolution, importez-le, sinon veuillez modifier son nom.",
+       "fileexists-forbidden": "Un fichier avec ce nom existe déjà et ne peut pas être écrasé.\nSi vous voulez toujours importer votre fichier, veuillez revenir en arrière et utiliser un autre nom. \n[[File:$1|thumb|center|$1]]",
+       "fileexists-shared-forbidden": "Un fichier portant ce nom existe déjà dans le dépôt de fichiers partagé.\nSi vous voulez toujours importer votre fichier, veuillez revenir en arrière et utiliser un autre nom. \n[[File:$1|thumb|center|$1]]",
        "file-exists-duplicate": "Ce fichier est un doublon {{PLURAL:$1|du fichier suivant|des fichiers suivants}} :",
-       "file-deleted-duplicate": "Un fichier identique à celui-ci ([[:$1]]) a déjà été supprimé. Vous devriez vérifier le journal des suppressions de ce fichier avant de l'importer à nouveau.",
+       "file-deleted-duplicate": "Un fichier identique à celui-ci ([[:$1]]) a déjà été supprimé. \nVous devriez vérifier le journal des suppressions de ce fichier avant de l'importer à nouveau.",
        "file-deleted-duplicate-notitle": "Un fichier identique à ce fichier a déjà été supprimé ainsi que le titre. \nVous devriez demander à quelqu'un la possibilité de vérifier le journal de ce fichier supprimé afin d'examiner la situation  avant de l'importer à nouveau.",
        "uploadwarning": "Attention !",
        "uploadwarning-text": "Modifiez la description du fichier et essayez de nouveau.",
        "uploaddisabled": "Désolé, l’import de fichiers est désactivé.",
        "copyuploaddisabled": "Import de fichier par URL désactivé.",
        "uploaddisabledtext": "L’import de fichiers est désactivé sur ce wiki.",
-       "php-uploaddisabledtext": "L'import de fichiers a été désactivé dans PHP. Vérifiez l'option de configuration file_uploads.",
+       "php-uploaddisabledtext": "L'import de fichiers est désactivé en PHP. Vérifiez l'option de configuration file_uploads.",
        "uploadscripted": "Ce fichier contient du code HTML ou un script qui pourrait être interprété de façon incorrecte par un navigateur web.",
        "upload-scripted-pi-callback": "Impossible de charger un fichier qui contient des instructions de traitement de feuille de style XML.",
        "uploaded-script-svg": "Élément scriptable « $1 » trouvé dans le fichier SVG téléchargé.",
        "filename-bad-prefix": "Le nom du fichier commence par <strong>« $1 »</strong> qui est typiquement un nom non-descriptif attribué automatiquement par les appareils photo numériques.\nVeuillez choisir un nom de fichier plus descriptif.",
        "filename-prefix-blacklist": " #<!-- laisser cette ligne telle quelle --><pre>\n# La syntaxe est la suivante :\n#  * Tout ce qui figure entre un caractère \"#\" jusqu’à la fin de la ligne est un commentaire ;\n#  * Toute ligne non vide est un préfixe typique de nom de fichier assigné automatiquement par les appareils numériques :\nCIMG # Casio\nDSC_ # Nikon\nDSCF # Fuji\nDSCN # Nikon\nDUW # certains téléphones mobiles\nIMG # générique\nJD # Jenoptik\nMGP # Pentax\nPICT # divers\n #</pre><!-- laisser cette ligne telle quelle -->",
        "upload-proto-error": "Protocole incorrect",
-       "upload-proto-error-text": "L’import requiert des URL commençant par <code>http://</code> ou <code>ftp://</code>.",
+       "upload-proto-error-text": "L’import à distance requiert que les URL commencent par <code>http://</code> ou <code>ftp://</code>.",
        "upload-file-error": "Erreur interne",
        "upload-file-error-text": "Une erreur interne est survenue en voulant créer un fichier temporaire sur le serveur. \nVeuillez contacter un [[Special:ListUsers/sysop|administrateur]].",
        "upload-misc-error": "Erreur d’import inconnue",
        "upload-dialog-button-upload": "Téléverser",
        "upload-form-label-infoform-title": "Détails",
        "upload-form-label-infoform-name": "Nom",
-       "upload-form-label-infoform-name-tooltip": "Un titre descriptif unique pour le fichier, qui servira comme nom de fichier. Vous pouvez utiliser du langage courant avec des espaces. Ne pas inclure l’extension du fichier.",
+       "upload-form-label-infoform-name-tooltip": "Un titre descriptif unique pour le fichier, qui servira comme nom de fichier. Vous pouvez utiliser le langage courant avec des espaces. Ne pas inclure l’extension du fichier.",
        "upload-form-label-infoform-description": "Description",
        "upload-form-label-infoform-description-tooltip": "Décrire brièvement tout ce qu’il y a de particulier concernant cette œuvre.\nPour une photo, mentionner les choses principales qui sont vues, l’occasion, ou l’endroit.",
        "upload-form-label-usage-title": "Utilisation",
        "upload-form-label-not-own-work-local-generic-local": "Vous pouvez aussi essayer [[Special:Upload|la page de téléchargement par défaut]].",
        "upload-form-label-own-work-message-generic-foreign": "Je comprends que je téléverse ce fichier vers un dépôt partagé. Je confirme agir en accord avec les conditions d’utilisation et les règles relatives aux licences de celui-ci.",
        "upload-form-label-not-own-work-message-generic-foreign": "Si vous n’êtes pas en mesure de téléverser ce fichier de façon conforme aux règles de ce dépôt partagé, veuillez fermer cette boîte de dialogue et essayer une autre méthode.",
-       "upload-form-label-not-own-work-local-generic-foreign": "Vous pouvez également essayer d’utiliser [[Special:Upload|la page de téléversement de {{SITENAME}}]], si les règles du site autorisent le téléversement du fichier.",
-       "backend-fail-stream": "Impossible de lire le fichier $1.",
-       "backend-fail-backup": "Impossible de sauvegarder le fichier $1.",
+       "upload-form-label-not-own-work-local-generic-foreign": "Vous pouvez également essayer d’utiliser [[Special:Upload|la page de téléversement de {{SITENAME}}]], si leur règles de site autorisent le téléversement du fichier.",
+       "backend-fail-stream": "Impossible de lire le fichier \"$1\".",
+       "backend-fail-backup": "Impossible de sauvegarder le fichier \"$1\".",
        "backend-fail-notexists": "Le fichier $1 n’existe pas.",
        "backend-fail-hashes": "Impossible d’obtenir les hachages du fichier pour comparaison.",
-       "backend-fail-notsame": "Un fichier différent existe déjà pour $1 .",
-       "backend-fail-invalidpath": "$1 n’est pas un chemin de stockage valide.",
-       "backend-fail-delete": "Impossible de supprimer le fichier $1.",
+       "backend-fail-notsame": "Un fichier différent existe déjà pour \"$1\" .",
+       "backend-fail-invalidpath": "« $1 » n’est pas un chemin de stockage valide.",
+       "backend-fail-delete": "Impossible de supprimer le fichier \"$1\".",
        "backend-fail-describe": "Impossible de modifier les métadonnées du fichier « $1 ».",
-       "backend-fail-alreadyexists": "Le fichier $1 existe déjà.",
-       "backend-fail-store": "Impossible de stocker le fichier $1 en $2.",
-       "backend-fail-copy": "Impossible de copier le fichier $1 en $2.",
-       "backend-fail-move": "Impossible de déplacer le fichier $1 en $2.",
+       "backend-fail-alreadyexists": "Le fichier \"$1\" existe déjà.",
+       "backend-fail-store": "Impossible de stocker le fichier \"$1\" en \"$2\".",
+       "backend-fail-copy": "Impossible de copier le fichier « $1 » en « $2 ».",
+       "backend-fail-move": "Impossible de déplacer le fichier \"$1\" en \"$2\".",
        "backend-fail-opentemp": "Impossible d’ouvrir le fichier temporaire.",
        "backend-fail-writetemp": "Impossible d’écrire dans le fichier temporaire.",
        "backend-fail-closetemp": "Impossible de fermer le fichier temporaire.",
-       "backend-fail-read": "Impossible de lire le fichier $1.",
-       "backend-fail-create": "Impossible d’écrire le fichier $1.",
-       "backend-fail-maxsize": "Impossible d’écrire le fichier $1 parce qu’il est plus grand {{PLURAL:$2|qu’un octet|que $2 octets}}.",
+       "backend-fail-read": "Impossible de lire le fichier \"$1\".",
+       "backend-fail-create": "Impossible d’écrire le fichier « $1 ».",
+       "backend-fail-maxsize": "Impossible d’écrire le fichier « $1 » parce qu’il est plus grand {{PLURAL:$2|qu’un octet|que $2 octets}}.",
        "backend-fail-readonly": "Le support de stockage « $1 » est actuellement en lecture seule. La raison indiquée est : <em>$2</em>",
        "backend-fail-synced": "Le fichier « $1 » est dans un état incohérent dans les supports de stockage internes",
        "backend-fail-connect": "Impossible de se connecter au support de stockage « $1 ».",
        "backend-fail-internal": "Une erreur inconnue s’est produite dans le support de stockage « $1 ».",
        "backend-fail-contenttype": "Impossible de déterminer le type de contenu du fichier à stocker en « $1 ».",
-       "backend-fail-batchsize": "Le support de stockage a fourni un lot de $1 {{PLURAL:$1|opération|opérations}} de fichier; la limite est $2 {{PLURAL:$2|opération|opérations}}.",
-       "backend-fail-usable": "Impossible de lire ou d’écrire le fichier « $1 » en raison de droits insuffisants ou répertoires/conteneurs manquants.",
+       "backend-fail-batchsize": "On a fourni au support de stockage un lot de $1 {{PLURAL:$1|opération|opérations}} de fichier; la limite est $2 {{PLURAL:$2|opération|opérations}}.",
+       "backend-fail-usable": "Impossible de lire ou d’écrire le fichier « $1 » en raison de droits insuffisants ou de répertoires/conteneurs manquants.",
        "filejournal-fail-dbconnect": "Impossible de se connecter à la base de données du journal pour le terminal de stockage « $1 ».",
        "filejournal-fail-dbquery": "Impossible de mettre à jour la base de données du journal pour le terminal de stockage « $1 ».",
        "lockmanager-notlocked": "Impossible de déverrouiller « $1 » ; elle n'est pas verrouillée.",
        "uploadstash-errclear": "La suppression des fichiers a échoué.",
        "uploadstash-refresh": "Actualiser la liste des fichiers",
        "uploadstash-thumbnail": "afficher la vignette",
+       "uploadstash-exception": "Impossible de stocker le téléchargement dans la réserve ($1) : « $2 ».",
        "invalid-chunk-offset": "Offset de segment non valide",
        "img-auth-accessdenied": "Accès refusé",
        "img-auth-nopathinfo": "PATH_INFO manquant.\nVotre serveur n'est pas paramétré pour transmettre cette information.\nIl fonctionne peut-être en CGI et ne supporte pas img_auth.\nVoir : https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization.",
        "img-auth-noread": "L'utilisateur n'a pas le droit en lecture sur « $1 ».",
        "http-invalid-url": "URL incorrecte : $1",
        "http-invalid-scheme": "Les URL avec le schéma « $1 » ne sont pas prises en charge.",
-       "http-request-error": "Erreur inconnue lors de l'envoi de la requête.",
+       "http-request-error": "Erreur inconnue lors de l'envoi de la requête HTTP.",
        "http-read-error": "Erreur de lecture HTTP.",
        "http-timed-out": "La requête HTTP a expiré.",
        "http-curl-error": "Erreur lors de la récupération de l'URL : $1",
        "http-bad-status": "Il y a eu un problème lors de la requête HTTP : $1 $2",
        "upload-curl-error6": "URL injoignable",
-       "upload-curl-error6-text": "L’URL fournie ne peut pas être atteinte. Veuillez vérifier que l’URL est correcte et que le site est en ligne.",
+       "upload-curl-error6-text": "L’URL fournie ne peut pas être atteinte. \nVeuillez vérifier que l’URL est correcte et que le site est en ligne.",
        "upload-curl-error28": "Dépassement du délai lors de l'import",
-       "upload-curl-error28-text": "Le site a mis trop longtemps à répondre. Vérifiez que le site est en ligne, attendez un peu et réessayez. Vous pouvez aussi réessayer à une heure de moindre affluence.",
+       "upload-curl-error28-text": "Le site a mis trop longtemps à répondre. \nVérifiez que le site est en ligne, attendez un peu et réessayez. \nVous pouvez aussi réessayer à une heure de moindre affluence.",
        "license": "Licence",
        "license-header": "Conditions d'utilisation",
        "nolicense": "Aucune licence sélectionnée",
        "statistics-edits-average": "Nombre moyen de modifications par page",
        "statistics-users": "[[Special:ListUsers|Utilisateurs]] enregistrés",
        "statistics-users-active": "Utilisateurs actifs",
-       "statistics-users-active-desc": "Utilisateurs ayant fait au moins une action durant {{PLURAL:$1|le dernier jours|les $1 derniers jours}}",
+       "statistics-users-active-desc": "Utilisateurs ayant fait au moins une action {{PLURAL:$1|il y a un jour|pendant les $1 derniers jours}}",
        "pageswithprop": "Pages avec une propriété de page",
        "pageswithprop-legend": "Pages avec une propriété de page",
        "pageswithprop-text": "Cette page liste les pages qui utilisent une propriété de page particulière.",
        "apisandbox-fullscreen-tooltip": "Étendre le panneau du bac à sable pour remplir la fenêtre du navigateur.",
        "apisandbox-unfullscreen": "Afficher la page",
        "apisandbox-unfullscreen-tooltip": "Réduire le panneau du bac à sable, pour que les liens de navigation de MediaWiki soient disponibles.",
-       "apisandbox-submit": "Faire la demande",
+       "apisandbox-submit": "Envoyer la requête",
        "apisandbox-reset": "Effacer",
        "apisandbox-retry": "Réessayer",
        "apisandbox-loading": "Chargement des informations du module \"$1\" de l'API...",
        "undeletehistorynoadmin": "Cette page a été supprimée.\nLe motif de la suppression est indiqué dans le résumé ci-dessous, avec les détails des utilisateurs qui ont modifié la page avant sa suppression.\nLe contenu effectif de ces versions supprimées n’est accessible qu’aux administrateurs.",
        "undelete-revision": "Version supprimée de $1 (version du $4 à $5) par $3 :",
        "undeleterevision-missing": "Version incorrecte ou manquante.\nVous avez peut-être un mauvais lien, ou la version a pu être restaurée ou supprimée de l’archive.",
+       "undeleterevision-duplicate-revid": "{{PLURAL:$1|Une révision n'a|$1 révisions n'ont}} pas pu être restaurée{{PLURAL:$1|car son|s car leur}}  <code>rev_id</code> était déjà en cours d'utilisation.",
        "undelete-nodiff": "Aucune version précédente trouvée.",
        "undeletebtn": "Restaurer",
        "undeletelink": "voir/restaurer",
        "undeletedrevisions": "$1 {{PLURAL:$1|version restaurée|versions restaurées}}",
        "undeletedrevisions-files": "$1 version{{PLURAL:$1||s}} et $2 fichier{{PLURAL:$2||s}} restauré{{PLURAL:$2||s}}",
        "undeletedfiles": "$1 {{PLURAL:$1|fichier restauré|fichiers restaurés}}",
-       "cannotundelete": "Échec de la restauration :\n$1",
+       "cannotundelete": "Certaines ou toutes les restitutions ont échoué:\n$1",
        "undeletedpage": "'''La page $1 a été restaurée.'''\n\nConsultez le [[Special:Log/delete|journal des suppressions]] pour obtenir la liste des récentes suppressions et restaurations.",
        "undelete-header": "Consultez le [[Special:Log/delete|journal des suppressions]] pour lister les pages récemment supprimées.",
        "undelete-search-title": "Rechercher les pages supprimées",
        "sp-contributions-newbies-sub": "Parmi les nouveaux comptes",
        "sp-contributions-newbies-title": "Contributions d'utilisateurs parmi les nouveaux comptes",
        "sp-contributions-blocklog": "journal des blocages",
-       "sp-contributions-suppresslog": "contributions masquées",
-       "sp-contributions-deleted": "contributions supprimées",
+       "sp-contributions-suppresslog": "contributions de l'{{GENDER:$1|utilisateur|utilisatrice}} supprimées",
+       "sp-contributions-deleted": "contributions de l’{{GENDER:$1|utilisateur|utilisatrice}} supprimées",
        "sp-contributions-uploads": "imports",
        "sp-contributions-logs": "journaux",
        "sp-contributions-talk": "discuter",
index ddc6770..c658811 100644 (file)
        "october-date": "$1 dhen Dàmhair",
        "november-date": "$1 dhen t-Samhain",
        "december-date": "$1 dhen Dùbhlachd",
+       "period-am": "m",
+       "period-pm": "f",
        "pagecategories": "{{PLURAL:$1|Roinn-seòrsa|Roinnean-seòrsa}}",
        "category_header": "Duilleagan san roinn-seòrsa \"$1\"",
        "subcategories": "Fo-roinnean-seòrsa",
        "mailerror": "Mearachd a' cur post: $1",
        "acct_creation_throttle_hit": "Chruthaich na h-aoighean air an uicidh seo {{PLURAL:$1|$1 chunntas|$1 chunntas|$1 cunntasan|$1 cunntas}} fon IP agad an-dè agus sin an àireamh as motha a tha ceadaichte. Chan urrainn do dh'aoighean eile on IP seo barrachd chunntasan a chruthachadh air sgàth sin.",
        "emailauthenticated": "Chaidh an seòladh puist-d agad a dhearbhadh $2 aig $3.",
-       "emailnotauthenticated": "Cha deach am post-d agad a dhearbhadh fhathast.\nCha dèid post-d a chur airson gin dhe na gleusan a leanas.",
-       "noemailprefs": "Sònraich post-d sna roghainnean agad gus na gleusan seo a chur an comas.",
+       "emailnotauthenticated": "Cha deach am post-d agad a dhearbhadh fhathast.\nCha dèid post-d a chur airson gin dhe na feartan a leanas.",
+       "noemailprefs": "Sònraich post-d sna roghainnean agad gus na feartan seo a chur an comas.",
        "emailconfirmlink": "Dearbhaich an seòladh puist-dhealain agad",
        "invalidemailaddress": "Chan urrainn dhuinn gabhail ris an t-seòladh seo a chionn 's gu bheil coltas cearr air.\nCuir a-steach seòladh san fhòrmat cheart no falamhaich an raon sin.",
        "cannotchangeemail": "Cha ghabh na puist-d a tha co-cheangailte ri cunntas atharrachadh air an uicipeid seo.",
        "pt-login-button": "Log a-steach",
        "pt-createaccount": "Cruthaich cunntas",
        "pt-userlogout": "Log a-mach",
-       "php-mail-error-unknown": "Mearachd nach aithne dhuinn sa ghleus mail() aig PHP.",
+       "php-mail-error-unknown": "Mearachd neo-aithichte san fheart mail() aig PHP.",
        "user-mail-no-addy": "Cha do ghabh am post-d a chur leis nach robh seòladh puist-d ann.",
        "user-mail-no-body": "Bha bodhaig na teachdaireachd bàn no air leth goirid.",
        "changepassword": "Atharraich facal-faire",
        "passwordreset-emailtext-user": "Dh'iarr an cleachdaiche $1 air {{SITENAME}} ath-shuidheachadh an fhacail-fhaire air {{SITENAME}} ($4). Tha {{PLURAL:$3|an cunntas-cleachdaiche|na cunntasan-cleachdaiche}} a leanas co-cheangailte ris an t-seòladh puist-d seo:\n\n$2\n\nFalbhaidh an ùine air {{PLURAL:$3|an fhacal-fhaire shealach|na faclan-faire sealach}} seo an ceann $5 {{PLURAL:$5|latha|latha|làithean|latha}}.\nBu chòir dhut logadh a-steach agus facal-faire ùr a thaghadh an-dràsta. Ma dh'iarr cuideigin eile seo no ma chuimhnich thu air an fhacal-fhaire agad 's mur eil thu airson atharrachadh tuilleadh, leig seachad an teachdaireachd seo 's lean ort leis an t-seann fhacal-fhaire.",
        "passwordreset-emailelement": "Ainm-cleachdaiche: \n$1\n\nFacal-faire sealach: \n$2",
        "passwordreset-emailsentemail": "Ma tha am post-d seo co-cheangailte ris a’ chunntas agad, thèid post-d airson ath-shuidheachadh an fhacail-fhaire a chur.",
-       "passwordreset-emailsent-capture": "Chaidh post-d a chum ath-shuidheachadh an fhacail-fhaire a chur agus chì thu sin gu h-ìosal.",
-       "passwordreset-emailerror-capture": "Chaidh post-d a chum ath-shuidheachadh an fhacail-fhaire a ghintinn agus chì thu sin gu h-ìosal ach cha b' urrainn dhuinn a chur dhan chleachdaiche: $1",
        "changeemail": "Atharraich no thoir air falbh an seòladh puist-d",
        "changeemail-header": "Lìon am foirm seo a dh’atharrachadh an t-seòlaidh phuist-d agad. Ma tha thu airson an co-cheangal eadar post-d sam bith is an cunntas agad a thoirt air falbh, fàg an seòladh ùr bàn nuair a chuireas tu am foirm.",
        "changeemail-no-info": "Feumaidh tu logadh a-steach mus dèan thu inntrigeadh dìreach dhan duilleag seo.",
        "minoredit": "Seo mùthadh beag",
        "watchthis": "Cum sùil air an duilleag seo",
        "savearticle": "Sàbhail an duilleag",
+       "publishpage": "Foillsich an duilleag",
+       "publishchanges": "Foillsich na mùthaidhean",
        "preview": "Ro-shealladh",
        "showpreview": "Seall an ro-shealladh",
        "showdiff": "Seall na mùthaidhean",
        "summary-preview": "Ro-shealladh a' ghearr-chunntais:",
        "subject-preview": "Ro-shealladh a’ chuspair:",
        "blockedtitle": "Tha an cleachdair air a bhacadh",
-       "blockedtext": "<strong>Chaidh an t-ainm-cleachdaiche no an seòladh IP agad a bhacadh.</strong>\n\n'S e $1 a chur am bacadh seo ort.\n{{GENDER:$1|Thug e|Thug i|Thugadh}} an cèill gun do {{GENDER:$1|rinn e|rinn i|rinneadh}} sin air sgàth an adhbhair seo: <em>$2</em>.\n\n* Toiseach a' bhacaidh: $8\n* Deireadh a' bhacaidh: $6\n* An neach air a bheil am bacadh: $7\n\n'S urrainn dhut fios a chur gu $1 no [[{{MediaWiki:Grouppage-sysop}}|rianair]] eile gus am bacadh seo a dheasbad.\nChan urrainn dhut an gleus \"Cuir post-d dhan chleachdaiche seo\" a chleachdadh ach ma tha seòladh puist-d dligheach ann an [[Special:Preferences|roghainnean a' chunntais agad]] agus mura deach bacadh a chur air a chleachdadh.\n'S e $3 an seòladh IP làithreach agus agus 's e #$5 ID a' bhacaidh.\nThoir iomradh air a' mhion-fhiosrachadh gu h-àrd ma chuireas tu ceist sam bith mu dhèidhinn.",
-       "autoblockedtext": "Chaidh an seòladh IP agad a bhacadh gu fèin-obrachail a chionn 's gun deach a chleachdadh le cuideigin eile a chaidh a bhacadh le $1.\n{{GENDER:$1|Thug e|Thug i|Thugadh}} an cèill gun do {{GENDER:$1|rinn e|rinn i|rinneadh}} sin air sgàth an adhbhair seo: \n\n:<em>$2</em>.\n\n* Toiseach a' bhacaidh: $8\n* Deireadh a' bhacaidh: $6\n* An neach air a bheil am bacadh: $7\n\n'S urrainn dhut fios a chur gu $1 no [[{{MediaWiki:Grouppage-sysop}}|rianair]] eile gus am bacadh seo a dheasbad.\n\nDh'fhaoidte nach urrainn dhut an gleus \"Cuir post-d dhan chleachdaiche seo\" a chleachdadh ach ma tha seòladh puist-d dligheach ann an [[Special:Preferences|roghainnean a' chunntais agad]] agus mura deach bacadh a chur air a chleachdadh.\n\n'S e $3 an seòladh IP làithreach agus agus 's e #$5 ID a' bhacaidh.\nThoir iomradh air a' mhion-fhiosrachadh gu h-àrd ma chuireas tu ceist sam bith mu dhèidhinn.",
+       "blockedtext": "<strong>Chaidh an t-ainm-cleachdaiche no an seòladh IP agad a bhacadh.</strong>\n\n'S e $1 a chur am bacadh seo ort.\n{{GENDER:$1|Thug e|Thug i|Thugadh}} an cèill gun do {{GENDER:$1|rinn e|rinn i|rinneadh}} sin air sgàth an adhbhair seo: <em>$2</em>.\n\n* Toiseach a' bhacaidh: $8\n* Deireadh a' bhacaidh: $6\n* An neach air a bheil am bacadh: $7\n\n'S urrainn dhut fios a chur gu $1 no [[{{MediaWiki:Grouppage-sysop}}|rianair]] eile gus am bacadh seo a dheasbad.\nChan urrainn dhut am feart \"Cuir post-d dhan chleachdaiche seo\" a chleachdadh ach ma tha seòladh puist-d dligheach ann an [[Special:Preferences|roghainnean a' chunntais agad]] agus mura deach bacadh a chur air a chleachdadh.\n'S e $3 an seòladh IP làithreach agus agus 's e #$5 ID a' bhacaidh.\nThoir iomradh air a' mhion-fhiosrachadh gu h-àrd ma chuireas tu ceist sam bith mu dhèidhinn.",
+       "autoblockedtext": "Chaidh an seòladh IP agad a bhacadh gu fèin-obrachail a chionn 's gun deach a chleachdadh le cuideigin eile a chaidh a bhacadh le $1.\n{{GENDER:$1|Thug e|Thug i|Thugadh}} an cèill gun do {{GENDER:$1|rinn e|rinn i|rinneadh}} sin air sgàth an adhbhair seo: \n\n:<em>$2</em>.\n\n* Toiseach a' bhacaidh: $8\n* Deireadh a' bhacaidh: $6\n* An neach air a bheil am bacadh: $7\n\n'S urrainn dhut fios a chur gu $1 no [[{{MediaWiki:Grouppage-sysop}}|rianair]] eile gus am bacadh seo a dheasbad.\n\nDh'fhaoidte nach urrainn dhut am feart \"Cuir post-d dhan chleachdaiche seo\" a chleachdadh ach ma tha seòladh puist-d dligheach ann an [[Special:Preferences|roghainnean a' chunntais agad]] agus mura deach bacadh a chur air a chleachdadh.\n\n'S e $3 an seòladh IP làithreach agus agus 's e #$5 ID a' bhacaidh.\nThoir iomradh air a' mhion-fhiosrachadh gu h-àrd ma chuireas tu ceist sam bith mu dhèidhinn.",
        "blockednoreason": "cha deach adhbhar a shònrachadh",
        "whitelistedittext": "Feumaidh tu $1 mus urrainn dhut duilleagan a dheasachadh.",
        "confirmedittext": "Feumaidh tu am post-d agad a dhearbhadh mus urrainn dhut duilleagan a dheasachadh.\nSuidhich is dearbhaich am post-d agad ann an [[Special:Preferences|roghainnean a' chleachdaiche]]",
        "undo-nochange": "Tha coltas gun deach am mùthadh seo a neo-dhèanamh mu thràth.",
        "undo-summary": "Neo-dhèan mùthadh $1 leis [[Special:Contributions/$2|$2]] ([[User talk:$2|an deasbaireachd]])",
        "undo-summary-username-hidden": "Neo-dhèan am mùthadh $1 le cleachdaiche falaichte",
-       "cantcreateaccounttitle": "Cha ghabh an cunntas a chruthachadh",
        "cantcreateaccount-text": "Chuir [[User:$3|$3]] bacadh air cruthachadh chunntasan on t-seòladh IP seo (<strong>$1</strong>).\n\nDh'innis $3 gun do rinn {{GENDER:$3|e|i}} seo air sgàth: <em>$2</em>",
        "cantcreateaccount-range-text": "Chuir [[User:$3|$3]] casg air daoine a tha airson cunntasan a chruthachadh on sheòlaidhean IP taobh a-staigh na rainse <strong>$1</strong> agus tha sin a' gabhail a-steach an t-seòlaidh IP agad-sa (<strong>$4</strong>).\n\nDh'innis $3 gun do {{GENDER:$1|rinn e|rinn i|rinneadh}} seo air sgàth an adhbhair seo: <em>$2</em>",
        "viewpagelogs": "Seall logaichean na duilleige seo",
        "prefs-skin": "Bian",
        "skin-preview": "Ro-shealladh",
        "datedefault": "Gun roghainnean",
-       "prefs-labs": "Gleusan nan deuchainn-lannan",
+       "prefs-labs": "Feartan nan deuchainn-lannan",
        "prefs-user-pages": "Duilleagan a' chleachdaiche",
        "prefs-personal": "Pròifil",
        "prefs-rc": "Mùthaidhean ùra",
        "zip-file-open-error": "Thachair mearachd le fosgladh an fhaidhle airson dearbhadh ZIP.",
        "zip-wrong-format": "Chan eil am faidhle sònraichte 'na fhaidhle ZIP.",
        "zip-bad": "Tha am faidhle ZIP coirbte no cha ghabh a leughadh air adhbhar eile air choireigin.\nChan urrainn dhuinn dearbhadh mar bu chòir a bheil e tèarainte gus nach eil.",
-       "zip-unsupported": "Tha am faidhle ZIP seo a' chleachdadh gleusan ZIP ris nach cuir MediaWiki taic.\nChan urrainn dhuinn dearbhadh mar bu chòir a bheil e tèarainte gus nach eil.",
+       "zip-unsupported": "Tha am faidhle ZIP seo a' chleachdadh feartan ZIP ris nach cuir MediaWiki taic.\nChan urrainn dhuinn dearbhadh mar bu chòir a bheil e tèarainte gus nach eil.",
        "uploadstash": "Tasgadan an luchdaidh suas",
        "uploadstash-summary": "Bheir an duilleag seo inntrigeadh dhut a dh'fhaidhlichean a chaidh a luchdadh suas no a tha 'gan luchdadh suas ach nach deach fhoillseachadh air an uicidh fhathast. Chan fhaic duine na faidhlichean seo ach an cleachdaiche a rinn an luchdadh suas.",
        "uploadstash-clear": "Glan na faidhlichean ann an tasgadan an luchdaidh suas",
        "emailccsubject": "Lethbhreac dhen teachdaireachd agad gu $1: $2",
        "emailsent": "Post-d air a chur",
        "emailsenttext": "Chaidh an teachdaireachd puist-d agad a chur.",
-       "emailuserfooter": "Chaidh am post-d seo a chur o $1 gu $2 leis a' ghleus \"{{int:emailuser}}\" air {{SITENAME}}.",
+       "emailuserfooter": "Chaidh am post-d seo a chur o $1 gu $2 leis an fheart \"{{int:emailuser}}\" air {{SITENAME}}.",
        "usermessage-summary": "A' fàgail teachdaireachd an t-siostaim.",
        "usermessage-editor": "Teachdaire an t-siostaim",
        "usermessage-template": "MediaWiki:UserMessage",
        "dellogpage": "Loga an sguabaidh às",
        "dellogpagetext": "Seo liosta dhe na chaidh a sguabadh às o chionn goirid.",
        "deletionlog": "loga an sguabaidh às",
-       "reverted": "Air tilleadh gu mùthadh roimhe",
+       "reverted": "Air aiseag gu mùthadh nas sine",
        "deletecomment": "Adhbhar:",
        "deleteotherreason": "Adhbhar eile/a bharrachd:",
        "deletereasonotherlist": "Adhbhar eile",
        "tooltip-ca-nstab-category": "Seall duilleag na roinn-seòrsa",
        "tooltip-minoredit": "Comharraich seo mar dheasachadh beag",
        "tooltip-save": "Sàbhail na mùthaidhean agad",
+       "tooltip-publish": "Foillsich na mùthaidhean agad",
        "tooltip-preview": "Ro-sheall na mùthaidhean agad; saoil an cleachd thu seo mus sàbhail thu iad?",
        "tooltip-diff": "Seall na mùthaidhean a chuir mi air an teacs",
        "tooltip-compareselectedversions": "Seall an diofar eadar an dà mhùthadh dhen duilleag seo a thagh thu",
        "markaspatrolledtext": "Cuir comharra freiceadain ris an duilleag seo",
        "markedaspatrolled": "Comharra freiceadain ris",
        "markedaspatrolledtext": "Chaidh comharra freiceadain a chur ris a' mhùthadh de [[:$1]] a thagh thu.",
-       "rcpatroldisabled": "Chaidh gleus nam freiceadan airson atharraichean o chionn goirid a chur à comas",
-       "rcpatroldisabledtext": "Tha gleus nam freiceadan airson atharraichean o chionn goirid à comas an-dràsta.",
+       "rcpatroldisabled": "Chaidh feart nam freiceadan airson atharraichean o chionn goirid a chur à comas",
+       "rcpatroldisabledtext": "Tha feart nam freiceadan airson atharraichean o chionn goirid à comas an-dràsta.",
        "markedaspatrollederror": "Cha ghabh comharra freiceadain a chur ris",
        "markedaspatrollederrortext": "Feumaidh tu mùthadh a shònrachadh gus comharra freiceadain a chur ris.",
        "markedaspatrollederror-noautopatrol": "Chan fhaod thu comharra freiceadain a chur ris na h-atharraichean agad fhèin.",
        "monthsall": "na h-uile",
        "confirmemail": "Dearbhaich an seòladh puist-dhealain",
        "confirmemail_noemail": "Cha dug thu seachad seòladh puist-d dligheach ann an [[Special:Preferences|roghainnean a' chleachdaiche]] agad.",
-       "confirmemail_text": "Iarraidh {{SITENAME}} ort gun dearbhaich thu an seòladh puist-d agad mus cleachd thu gleusan puist-d.\nCleachd am putan gu h-ìosal gus post-d dearbhaidh a chur dhan t-seòladh agad.\nBidh ceangal le còd sa phost-d ud;\nluchdaich an ceangal sa bhrabhsair agad airson dearbhadh gu bheil an seòladh puist-d agad dligheach.",
+       "confirmemail_text": "Iarraidh {{SITENAME}} ort gun dearbhaich thu an seòladh puist-d agad mus cleachd thu feartan puist-d.\nCleachd am putan gu h-ìosal gus post-d dearbhaidh a chur dhan t-seòladh agad.\nBidh ceangal le còd sa phost-d ud;\nluchdaich an ceangal sa bhrabhsair agad airson dearbhadh gu bheil an seòladh puist-d agad dligheach.",
        "confirmemail_pending": "Chaidh còd dearbhaidh a chur thugad air a' phost-d mar-thà;\nma tha thu air a' chunntas agad a chruthachadh o chionn goirid, 's math dh'fhaoidte gum b' feairrde thu feitheamh mionaid no dhà ach an ruig e thu mus iarr thu còd ùr.",
        "confirmemail_send": "Cuir còd dearbhaidh thugam",
        "confirmemail_sent": "Chaidh post-d dearbhaidh a chur.",
-       "confirmemail_oncreate": "Chaidh còd dearbhaidh a chur dhan t-seòladh puist-d agad.\nChan eil thu feumach air a' chòd seo airson logadh a-steach, ach feumaidh tu a thoirt seachad mus cleachd thu gleus sam bith san uicidh a chleachdas post-d.",
+       "confirmemail_oncreate": "Chaidh còd dearbhaidh a chur dhan t-seòladh puist-d agad.\nChan eil thu feumach air a' chòd seo airson logadh a-steach, ach feumaidh tu a thoirt seachad mus cleachd thu feart sam bith san uicidh a chleachdas post-d.",
        "confirmemail_sendfailed": "Cha deach le {{SITENAME}} post-d dearbhaidh a chur thugad.\nDearbhaich nach eil caractar mì-dhligheach san t-seòladh puist-d agad.\n\nSeo na thill an t-inneal puist-d: $1",
        "confirmemail_invalid": "Tha an còd dearbhaidh mì-dhligheach.\n'S dòcha gun do dh'fhalbh an ùine air.",
        "confirmemail_needlogin": "$1 gus an seòladh puist-d agad a dhearbhadh.",
        "confirmemail_success": "Chaidh an seòladh puist-d agad a dhearbhadh.\nFaodaidh tu [[Special:UserLogin|logadh a-steach]] a-nis 's tlachd a ghabhail às an uicidh.",
        "confirmemail_loggedin": "Tha an seòladh puist-d agad air a dhearbhadh a-nis.",
        "confirmemail_subject": "Dearbhadh an t-seòlaidh puist-d air {{SITENAME}}",
-       "confirmemail_body": "Chlàraich chuideigin - 's sinne an dùil gur e tusa a bh' ann - cunntas \"$2\"\nair {{SITENAME}} leis an t-seòladh puist-d seo on t-seòladh IP $1.\n\nGus dearbhadh gur an agad fhèin a tha an cunntas seo agus gus na gleusan puist-d\na ghnìomhachadh air {{SITENAME}}, fosgail an ceangal seo sa bhrabhsair agad:\n\n$3\n\nMur e *tusa* a bh' ann a chlàraich an cunntas seo, lean air a' cheangal seo\ngus sgur dhen dearbhadh leis a' phost-d:\n\n$5\n\nFalbhaidh an ùine air a' chòd dearbhaidh seo $4.",
-       "confirmemail_body_changed": "Dh'atharraich chuideigin - 's sinne an dùil gur e tusa a bh' ann - an seòladh puist-d\naig a' chunntas \"$2\" air {{SITENAME}} dhan t-seòladh puist-d seo on t-seòladh IP $1.\n\nGus dearbhadh gur an agad fhèin a tha an cunntas seo agus gus na gleusan puist-d\na ghnìomhachadh às ùr air {{SITENAME}}, fosgail an ceangal seo sa bhrabhsair agad:\n\n$3\n\nMur e *tusa* a bh' ann a chlàraich an cunntas seo, lean air a' cheangal seo\ngus sgur dhen dearbhadh leis a' phost-d:\n\n$5\n\nFalbhaidh an ùine air a' chòd dearbhaidh seo $4.",
-       "confirmemail_body_set": "Shuidhich chuideigin - 's sinne an dùil gur e tusa a bh' ann - an seòladh puist-d\naig a' chunntas \"$2\" air {{SITENAME}} dhan t-seòladh puist-d seo on t-seòladh IP $1.\n\nGus dearbhadh gur an agad fhèin a tha an cunntas seo agus gus na gleusan puist-d\na ghnìomhachadh air {{SITENAME}}, fosgail an ceangal seo sa bhrabhsair agad:\n\n$3\n\nMur e *tusa* a bh' ann a chlàraich an cunntas seo, lean air a' cheangal seo\ngus sgur dhen dearbhadh leis a' phost-d:\n\n$5\n\nFalbhaidh an ùine air a' chòd dearbhaidh seo $4.",
+       "confirmemail_body": "Chlàraich chuideigin - 's sinne an dùil gur e tusa a bh' ann - cunntas \"$2\"\nair {{SITENAME}} leis an t-seòladh puist-d seo on t-seòladh IP $1.\n\nGus dearbhadh gur an agad fhèin a tha an cunntas seo agus gus na feartan puist-d\na ghnìomhachadh air {{SITENAME}}, fosgail an ceangal seo sa bhrabhsair agad:\n\n$3\n\nMur e *tusa* a bh' ann a chlàraich an cunntas seo, lean air a' cheangal seo\ngus sgur dhen dearbhadh leis a' phost-d:\n\n$5\n\nFalbhaidh an ùine air a' chòd dearbhaidh seo $4.",
+       "confirmemail_body_changed": "Dh'atharraich chuideigin - 's sinne an dùil gur e tusa a bh' ann - an seòladh puist-d\naig a' chunntas \"$2\" air {{SITENAME}} dhan t-seòladh puist-d seo on t-seòladh IP $1.\n\nGus dearbhadh gur an agad fhèin a tha an cunntas seo agus gus na feartan puist-d\na ghnìomhachadh às ùr air {{SITENAME}}, fosgail an ceangal seo sa bhrabhsair agad:\n\n$3\n\nMur e *tusa* a bh' ann a chlàraich an cunntas seo, lean air a' cheangal seo\ngus sgur dhen dearbhadh leis a' phost-d:\n\n$5\n\nFalbhaidh an ùine air a' chòd dearbhaidh seo $4.",
+       "confirmemail_body_set": "Shuidhich chuideigin - 's sinne an dùil gur e tusa a bh' ann - an seòladh puist-d\naig a' chunntas \"$2\" air {{SITENAME}} dhan t-seòladh puist-d seo on t-seòladh IP $1.\n\nGus dearbhadh gur an agad fhèin a tha an cunntas seo agus gus na feartan puist-d\na ghnìomhachadh air {{SITENAME}}, fosgail an ceangal seo sa bhrabhsair agad:\n\n$3\n\nMur e *tusa* a bh' ann a chlàraich an cunntas seo, lean air a' cheangal seo\ngus sgur dhen dearbhadh leis a' phost-d:\n\n$5\n\nFalbhaidh an ùine air a' chòd dearbhaidh seo $4.",
        "confirmemail_invalidated": "Chaidh sgur de dhearbhadh an t-seòlaidh puist-d",
        "invalidateemail": "Sguir de dhearbhadh an t-seòlaidh puist-d",
        "scarytranscludedisabled": "[Tha gabhail a-steach 'na iomradh eadar-uicidh à comas]",
index f729895..5d7b797 100644 (file)
@@ -22,7 +22,8 @@
                        "VaiPolaSombra",
                        "Macofe",
                        "Banjo",
-                       "Josep Maria Roca Peña"
+                       "Josep Maria Roca Peña",
+                       "Luan"
                ]
        },
        "tog-underline": "Subliñar as ligazóns:",
        "passwordreset-emailelement": "Nome de usuario: \n$1\n\nContrasinal temporal: \n$2",
        "passwordreset-emailsentemail": "Se esta é unha dirección de correo electrónico asociada á súa conta, entón enviarase un correo electrónico para o restablecemento do seu contrasinal.",
        "passwordreset-emailsentusername": "Se hai unha dirección de correo electrónico asociada con este nome de usuario, entón enviarase un correo electrónico para o restablecemento do contrasinal.",
-       "passwordreset-emailsent-capture": "Enviouse un correo electrónico de restablecemento do contrasinal, mostrado a continuación.",
-       "passwordreset-emailerror-capture": "Xerouse un correo electrónico de restablecemento do contrasinal, mostrado a continuación, pero o envío {{GENDER:$2|ao usuario|á usuaria}} fallou: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|O correo de reinicialización do contrasinal foi enviado|Os correos de reinicialización do contrasinal foron enviados}}. {{PLURAL:$1|O nome de usuario e contrasinal móstrase abaixo|A lista de nomes de usuarios e contrasinais móstranse abaixo}}.",
        "passwordreset-emailerror-capture2": "O envío do correo {{GENDER:$2|ó usuario|á usuaria}} fallou: $1 {{PLURAL:$3|O nome de usuario e contrasinal móstrase abaixo|A lista de usuarios e contrasinais móstranse abaixo}}.",
        "passwordreset-nocaller": "Cómpre proporcionar un chamador",
        "passwordreset-nodata": "Non se indicou o nome de usuario ou a dirección de correo electrónico",
        "changeemail": "Cambiar ou eliminar o enderezo de correo electrónico",
        "changeemail-header": "Encha este formulario para cambiar o seu enderezo de correo electrónico. Se vostede quere eliminar a asociación da dirección de correo electrónico da súa conta, deixe en branco a nova dirección de correo electrónico cando envíe o formulario.",
-       "changeemail-passwordrequired": "Terá que escribir o seu contrasinal para confirmar este cambio.",
        "changeemail-no-info": "Debe rexistrarse para acceder directamente a esta páxina.",
        "changeemail-oldemail": "Enderezo de correo electrónico actual:",
        "changeemail-newemail": "Novo enderezo de correo electrónico:",
        "undo-nochange": "Semella que alguén xa desfixo a edición.",
        "undo-summary": "Desfíxose a edición $1 de [[Special:Contributions/$2|$2]] ([[User talk:$2|conversa]])",
        "undo-summary-username-hidden": "Desfíxose a edición $1 dun usuario agochado",
-       "cantcreateaccounttitle": "Non pode crear unha conta de usuario",
        "cantcreateaccount-text": "A creación de contas desde este enderezo IP ('''$1''') foi bloqueada por [[User:$3|$3]].\n\nA razón dada por $3 foi ''$2''",
        "cantcreateaccount-range-text": "O usuario [[User:$3|$3]] bloqueou a creación de contas desde enderezos IP no rango <strong>$1</strong>, no que se inclúe o seu enderezo IP (<strong>$4</strong>).\n\nA razón que deu $3 foi <em>$2</em>.",
        "viewpagelogs": "Ver os rexistros desta páxina",
        "uploadstash-errclear": "Fallou o borrado de ficheiros.",
        "uploadstash-refresh": "Actualizar a lista de ficheiros",
        "uploadstash-thumbnail": "ver miniatura",
+       "uploadstash-exception": "Imposible gardar a subida na reserva ($1): \"$2\".",
        "invalid-chunk-offset": "Desprazamento inválido do fragmento",
        "img-auth-accessdenied": "Acceso rexeitado",
        "img-auth-nopathinfo": "Falta a PATH_INFO.\nO seu servidor non está configurado para pasar esta información.\nPode ser que estea baseado en CGI e non soporte img_auth.\nVéxase https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization.",
index 81dec3f..090585a 100644 (file)
        "powersearch-legend": "𐍃𐍉𐌺𐌴𐌹",
        "preferences": "𐌼𐌴𐌹𐌽𐍉𐍃 𐌱𐍂𐌿𐌺𐌾𐌰𐌼𐌰𐌹𐌳𐌴𐌹𐌽𐌴𐌹𐍃",
        "mypreferences": "𐌲𐌰𐌻𐌴𐌹𐌺𐌰𐌽𐌳𐌴𐌹𐌽𐍃 𐍅𐌰𐌹𐌷𐍄𐍃",
-       "prefs-skin": "Seidofill",
+       "prefs-skin": "𐍆𐌹𐌻𐌻",
        "skin-preview": "Faúrsaiƕa",
-       "saveprefs": "Melja",
+       "saveprefs": "𐌲𐌰𐍆𐌰𐍃𐍄",
        "searchresultshead": "𐍃𐍉𐌺𐌴𐌹",
        "grouppage-sysop": "{{ns:project}}:𐍃𐌴𐌹𐌳𐍉𐍆𐌰𐌸𐍃",
        "right-writeapi": "𐌱𐍂𐌿𐌺𐌴𐌹𐌽𐍃 API 𐌼𐌴𐌻𐌴𐌹𐌽𐌰𐌹𐍃",
        "diff": "𐌼𐌹𐍃𐍃",
        "hist": "𐍃𐍀𐌹𐌻𐌻",
        "hide": "𐍆𐌹𐌻𐌷𐌰𐌽",
-       "show": "ð\90\8c·ð\90\8c¿ð\90\8c»ð\90\8c¾ð\90\8c°ð\90\8c½",
+       "show": "ð\90\8c°ð\90\8d\84ð\90\8c°ð\90\8c¿ð\90\8c²ð\90\8c´ð\90\8c¹",
        "minoreditletter": "l",
        "newpageletter": "N",
        "boteditletter": "b",
        "mimesearch": "MIME 𐍃𐍉𐌺𐌴𐌹",
        "listredirects": "𐍄𐌰𐌻𐌰 𐌰𐍆 𐍄𐌰𐌹𐌺𐌾𐌰𐌽𐍃𐌴𐌹𐌳𐍉𐍃",
        "randompage": "𐌸𐌿𐍃 𐌿𐌽𐌺𐌿𐌽𐌸𐍃 𐌻𐌰𐌿𐍆𐍃",
-       "statistics": "ð\90\8d\83ð\90\8c´ð\90\8c¹ð\90\8c³ð\90\8d\89ð\90\8d\83ð\90\8d\84ð\90\8c°ð\90\8d\84ð\90\8c¹ð\90\8d\83ð\90\8d\84ð\90\8c¹ð\90\8cº",
+       "statistics": "ð\90\8d\82ð\90\8c°ð\90\8c¸ð\90\8c¾ð\90\8d\89ð\90\8c½ð\90\8d\83",
        "brokenredirects-edit": "𐌹𐌽𐌼𐌰𐌹𐌳𐌴𐌹",
        "brokenredirects-delete": "(𐍄𐌰𐌹𐍂𐌰𐌽)",
        "nbytes": "$1 {{PLURAL:$1|𐌱𐌹𐍄|𐌱𐌰𐍄𐌰}}",
        "nlinks": "$1 {{PLURAL:$1|𐌲𐌰𐍅𐌹𐍃𐍃|𐌲𐌰𐍅𐌹𐍃𐍃𐌴𐌹𐍃}}",
        "nmembers": "$1 {{PLURAL:$1|niutand|niutanda}}",
        "wantedpages": "𐌲𐌰𐌹𐍂𐌽𐌹𐌳𐌰𐌹 𐌻𐌰𐌿𐌱𐍉𐍃",
-       "shortpages": "ð\90\8c»ð\90\8c´ð\90\8c¹ð\90\8d\84ð\90\8c¹ð\90\8c»ð\90\8c° ð\90\8d\83ð\90\8c´ð\90\8c¹ð\90\8c³𐍉𐍃",
+       "shortpages": "ð\90\8c¼ð\90\8c°ð\90\8c¿ð\90\8d\82ð\90\8c²ð\90\8c°ð\90\8c¹ ð\90\8c»ð\90\8c°ð\90\8c¿ð\90\8c±𐍉𐍃",
        "longpages": "𐌻𐌰𐌲𐌲𐌰𐌹 𐌻𐌰𐌿𐌱𐍉𐍃",
        "listusers": "𐍂𐌴𐌲𐌹𐍃𐍄𐍂𐌴𐍂𐌰𐌳𐌴 𐌱𐍂𐌿𐌺𐌾𐌰𐌽𐌳𐍃",
        "newpages": "𐌽𐌹𐌿𐌾𐌰𐌹 𐌻𐌰𐌿𐌱𐍉𐍃",
        "undeleteviewlink": "𐍃𐌰𐌹𐍈𐌹𐍃",
        "undelete-search-submit": "𐍃𐍉𐌺𐌴𐌹",
        "namespace": "𐌽𐌰𐌼𐌰𐍂𐌿𐌼:",
-       "invert": "Afwandjan kustus",
+       "invert": "𐌲𐌰𐍅𐌰𐌽𐌳𐌴𐌹 𐌸𐌰𐍄𐌰 𐌲𐌰𐍅𐌰𐌻𐌹𐌳𐍉",
        "blanknamespace": "(𐍆𐍂𐌿𐌼𐌹𐍃𐍄𐍃)",
        "contributions": "𐌱𐌹𐌰𐌿𐌺𐌰𐌹𐌽𐌴𐌹𐍃 𐌱𐍂𐌿𐌺𐌾𐌰𐌽𐌳𐌹𐍃 {{{{GENDER:$1|User}}",
        "mycontris": "𐌱𐌹𐌰𐌿𐌺𐌰𐌹𐌽𐌴𐌹𐍃",
        "ipbreason": "𐍆𐌰𐌹𐍂𐌹𐌽𐌰:",
        "ipboptions": "𐌱 𐌰𐍅𐍂𐌰:2 hours, 𐌰 𐌳𐌰𐌲𐍃:1 day, 𐌲 𐌳𐌰𐌲𐍉𐍃:3 days, 𐌰 𐍅𐌹𐌺𐍉:1 week, 𐌱 𐍅𐌹𐌺𐍉𐌽𐍃:2 weeks, 𐌰 𐌼𐌴𐌽𐍉𐌸𐍃:1 month, 𐌲 𐌼𐌴𐌽𐍉𐌸𐍉𐍃:3 months, 𐌵 𐌼𐌴𐌽𐍉𐌸𐍉𐍃:6 months, 𐌰 𐌾𐌴𐍂:1 year, 𐌹𐌽𐌿𐍄𐍂𐌹𐌲𐌲𐌴𐌽𐌳𐌴𐌹𐍃:infinite",
        "ipblocklist-submit": "𐍃𐍉𐌺𐌴𐌹",
-       "infiniteblock": "ajukduþs",
+       "infiniteblock": "𐌰𐌽𐌳𐌰𐌻𐌰𐌿𐍃",
        "blocklink": "𐍆𐌰𐌿𐍂𐌳𐌰𐌼𐌼𐌴𐌹",
        "unblocklink": "𐍅𐌰𐌽𐌳𐌾𐌰𐌽",
        "change-blocklink": "𐌲𐌰𐌼𐌰𐌹𐌳𐌾𐌰𐌽 𐍅𐌰𐌿𐍂𐌾𐌰𐍅𐌰𐌳𐌳𐌾𐌿𐍃",
        "newtitle": "𐌽𐌹𐌿𐌾𐌹 𐌿𐍆𐌰𐍂𐌼𐌴𐌻𐌹:",
        "move-watch": "𐌰𐍄𐍅𐌹𐍄 𐌱𐍂𐌿𐌽𐌽𐌰𐌻𐌰𐌿𐌱𐌰 𐌾𐌰𐌷 𐌼𐌿𐌽𐌳𐍂𐌴𐌹𐌻𐌰𐌿𐌱𐌰",
        "movepagebtn": "𐍃𐌺𐌹𐌿𐌱𐌰 𐍃𐌴𐌹𐌳𐍉",
-       "movelogpage": "Log af skiubans",
+       "movelogpage": "𐌼𐌹𐌸𐍃𐌰𐍄𐌴𐌹 𐌲𐌰𐍆𐌰𐍃𐍄𐌰𐌹𐌽",
        "movereason": "𐍆𐌰𐌹𐍂𐌹𐌽𐌰:",
        "revertmove": "𐍂𐌰𐌹𐌳𐌾𐌰𐌽",
        "export": "𐌿𐍄𐌱𐌰𐌹𐍂 𐌻𐌰𐌿𐌱𐌰𐌽𐍃",
index 807ce58..80cf567 100644 (file)
        "passwordreset-emailtext-user": "વેબસાઈટ  {{SITENAME}} ના વપરાશકર્તા $1 એ તમારા {{SITENAME}} ($4) નો પાસવર્ડ રિસેટ કરવાની રજૂઆત કરી છે. આ ઈમેઈલ એડ્રેસ સાથે {{PLURAL:$3|નું ખાતું|ના ખાતા}} જોડાયેલ છે.\n\n$2\n\n{{PLURAL:$3|આ કામચલાઉ પાસવર્ડ|આ બધા કામચલાઉ પાસવર્ડ}} {{PLURAL:$5|એક દિવસ|$5 દિવસ}} માં નષ્ટ થઇ જશે. તમારે અત્યારે જ ખાતું ખોલીને નવો પાસવર્ડ સેટ કરી લેવો જોઈએ .જો કોઈ બીજા એ આ રજૂઆત કરી હોય, અથવા જો તમને પોતાનો અસલ પાસવર્ડ યાદ હોય, અને તેને બદલવા નથી માગતા, તો આ સંદેશાને જતો કરીને પોતાના અસલ પાસવર્ડ ને વાપરી શકો છો..",
        "passwordreset-emailelement": "વપરાશકર્તા નામ: \n$1\n\nકામચલાઉ પાસવર્ડ: \n$2",
        "passwordreset-emailsentemail": "પાસવર્ડ બદલવાનો ઇમેલ મોકલવામાં આવ્યો છે.",
-       "passwordreset-emailsent-capture": "પાસવર્ડ બદલવાનો ઇમેલ મોકલવામાં આવ્યો છે, જે નીચે પ્રમાણે છે.",
-       "passwordreset-emailerror-capture": "પાસવર્ડ ફરી ગોઠવવા માટેનો ઇમેલ બનાવવામાં આવ્યો છે, જે નીચે પ્રમાણે છે, પરંતુ તે {{GENDER:$2|સભ્ય}}ને મોકલવામાં નિષ્ફળ થયો છે: $1",
        "changeemail": "ઇમેલ સરનામું બદલો",
        "changeemail-header": "તમારા ખાતાનું ઇમેલ સરનામું બદલો",
        "changeemail-no-info": "બારોબાર આ પાનું જોવા માટે પ્રવેશ કરવો આવશ્યક છે.",
        "undo-failure": "વચ્ચે થયેલા અન્ય ફેરફાર થવાને કારણે આ ફેરફારો ઉલટાવી ન શકાયા",
        "undo-norev": "ફેરફાર સાચવી ન શકાયો કેમકે તે અસ્તિત્વમાં નથી અથવા તો ભૂંસી નખાયો છે.",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|talk]])એ કરેલો ફેરફાર $1 પાછો વાળ્યો",
-       "cantcreateaccounttitle": "ખાતું ખોલી શકાય તેમ નથી",
        "cantcreateaccount-text": "આ IP સરનામા  ('''$1''') પર નવા ખાતાની રચના પર   [[User:$3|$3]] દ્વારા રોક લગાવાઇ છે.\n\n\n$3 દ્વારા અપાયેલ કારણ છે ''$2''",
        "viewpagelogs": "આ પાનાનાં લૉગ જુઓ",
        "nohistory": "આ પાનાનાં ફેરફારનો ઇતિહાસ નથી.",
index b4b9c89..d12fc51 100644 (file)
        "passwordreset-emailelement": "שם משתמש:\n$1\n\nסיסמה זמנית:\n$2",
        "passwordreset-emailsentemail": "אם כתובת הדואר האלקטרוני הזאת משויכת לחשבון שלך, אז יישלח דואר אלקטרוני לאיפוס הסיסמה.",
        "passwordreset-emailsentusername": "אם יש כתובת דואר אלקטרוני שמשויכת לשם המשתמש הזה, אז יישלח דואר אלקטרוני לאיפוס הסיסמה.",
-       "passwordreset-emailsent-capture": "נשלח דואר אלקטרוני לאיפוס הסיסמה, והוא מוצג להלן.",
-       "passwordreset-emailerror-capture": "נוצר דואר אלקטרוני לאיפוס הסיסמה, והוא מוצג להלן, אך שליחתו ל{{GENDER:$2|משתמש|משתמשת}} נכשלה: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|דוא\"ל איפוס הסיסמה נשלח|הודעות דוא\"ל של איפוס הסיסמה נשלחו}}. {{PLURAL:$1|שם המשתמשים והסיסמה מוצגים|רשימה של שמות המשתמשים והסיסמאות מוצגת}} להלן.",
        "passwordreset-emailerror-capture2": "לא ניתן היה לשלוח דוא\"ל ל{{GENDER:$2|משתמש|משתמשת}}: $1 {{PLURAL:$3|שם המשתמש והסיסמה מוצגים|רשימה של שמות המשתמשים והסיסמאות מוצגת}} להלן.",
        "passwordreset-nocaller": "לא סופק הקורא הנדרש",
        "passwordreset-nodata": "לא סופק שם משתמש או כתובת דוא\"ל",
        "changeemail": "שינוי או הסרת כתובת דוא\"ל",
        "changeemail-header": "יש למלא את הטופס הזה כדי לשנות את כתובת הדוא\"ל שלך. אם ברצונך להימנע משיוך כתובת דוא\"ל כלשהי לחשבון שלך, יש להשאיר את שדה כתובת הדוא\"ל החדשה ריק בעת שליחת הטופס.",
-       "changeemail-passwordrequired": "יש להקליד את הסיסמה שלך כדי לאשר את השינוי.",
        "changeemail-no-info": "נדרשת כניסה לחשבון כדי לגשת לדף זה ישירות.",
        "changeemail-oldemail": "כתובת דוא\"ל נוכחית:",
        "changeemail-newemail": "כתובת דוא\"ל חדשה:",
        "undo-nochange": "נראה שהעריכה כבר בוטלה.",
        "undo-summary": "ביטול גרסה $1 של [[Special:Contributions/$2|$2]] ([[User talk:$2|שיחה]])",
        "undo-summary-username-hidden": "ביטול גרסה $1 של משתמש מוסתר",
-       "cantcreateaccounttitle": "לא ניתן ליצור את החשבון",
        "cantcreateaccount-text": "אפשרות יצירת החשבונות מכתובת ה־IP הזאת (<strong>$1</strong>) נחסמה על־ידי [[User:$3|$3]].\n\nהסיבה שניתנה על־ידי $3 היא \"$2\".",
        "cantcreateaccount-range-text": "אפשרות יצירת החשבונות מכתובות IP בתוך הטווח <strong>$1</strong>, כולל כתובת ה־IP שלך (<strong>$4</strong>), נחסמה על־ידי [[User:$3|$3]].\n\nהסיבה שניתנה על־ידי $3 היא \"$2\".",
        "viewpagelogs": "הצגת יומנים עבור דף זה",
        "uploadstash-errclear": "מחיקת הקבצים נכשלה.",
        "uploadstash-refresh": "רענון רשימת הקבצים",
        "uploadstash-thumbnail": "הצגת תמונה ממוזערת",
+       "uploadstash-exception": "לא ניתן לאחסן את ההעלאה בסליק ($1): \"$2\".",
        "invalid-chunk-offset": "היסט גוש לא תקין",
        "img-auth-accessdenied": "הגישה נדחתה",
        "img-auth-nopathinfo": "PATH_INFO חסר.\nהשרת אינו מוגדר להעברת מידע זה.\nייתכן שהוא מבוסס על CGI ולכן אינו יכול לתמוך ב־img_auth.\nראו https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization.",
        "undeletehistorynoadmin": "דף זה נמחק.\nהסיבה למחיקה מוצגת בתקציר שלמטה, וגם פרטים על המשתמשים שערכו את הדף לפני שהוא נמחק.\nהטקסט של הגרסאות הללו זמין למפעילי מערכת בלבד.",
        "undelete-revision": "גרסה שנמחקה מהדף $1 (מ־$5, $4) מאת $3:",
        "undeleterevision-missing": "הגרסה שגויה או חסרה. ייתכן שמדובר בקישור שבור, או שהגרסה שוחזרה או הוסרה מהארכיון.",
+       "undeleterevision-duplicate-revid": "לא ניתן היה לשחזר {{PLURAL:$1|גרסה אחת|$1 גרסאות}}, כיוון ששדה <code>rev_id</code> {{PLURAL:$1|שלה|שלהן}} כבר נמצא בשימוש.",
        "undelete-nodiff": "לא נמצאה גרסה קודמת.",
        "undeletebtn": "שחזור",
        "undeletelink": "הצגה/שחזור",
        "undeletedrevisions": "{{PLURAL:$1|שוחזרה גרסה אחת|שוחזרו $1 גרסאות}}",
        "undeletedrevisions-files": "{{PLURAL:$1|גרסה אחת|$1 גרסאות}} ו{{PLURAL:$2|קובץ אחד|־$2 קבצים}} שוחזרו",
        "undeletedfiles": "{{PLURAL:$1|שוחזר קובץ אחד|שוחזרו $1 קבצים}}",
-       "cannotundelete": "השחזור נכשל:\n$1",
+       "cannotundelete": "השחזור (או חלק ממנו) נכשל:\n$1",
        "undeletedpage": "<strong>הדף $1 שוחזר</strong>\n\nראו את [[Special:Log/delete|יומן המחיקות]] לרשימה של המחיקות והשחזורים שבוצעו לאחרונה.",
        "undelete-header": "{{GENDER:|ראה|ראי|ראו}} את [[Special:Log/delete|יומן המחיקות]] לרשימה של דפים שנמחקו לאחרונה.",
        "undelete-search-title": "חיפוש דפים שנמחקו",
        "sp-contributions-newbies-sub": "עבור משתמשים חדשים",
        "sp-contributions-newbies-title": "תרומות של משתמשים חדשים",
        "sp-contributions-blocklog": "יומן חסימות",
-       "sp-contributions-suppresslog": "תרומות משתמש מועלמות",
-       "sp-contributions-deleted": "תרומות משתמש מחוקות",
+       "sp-contributions-suppresslog": "תרומות {{GENDER:$1|משתמש|משתמשת}} מועלמות",
+       "sp-contributions-deleted": "תרומות {{GENDER:$1|משתמש|משתמשת}} מחוקות",
        "sp-contributions-uploads": "העלאות",
        "sp-contributions-logs": "יומנים",
        "sp-contributions-talk": "שיחה",
        "tags-active-yes": "כן",
        "tags-active-no": "לא",
        "tags-source-extension": "הוגדר על־ידי הרחבה",
-       "tags-source-manual": "×\94וחל באופן ידני על־ידי משתמשים ובוטים",
+       "tags-source-manual": "×\9eוחל באופן ידני על־ידי משתמשים ובוטים",
        "tags-source-none": "אינו בשימוש כעת",
        "tags-edit": "עריכה",
        "tags-delete": "מחיקה",
index 17f116b..e4b81bf 100644 (file)
        "passwordreset-emailtext-user": "Suradnik $1 na {{SITENAME}} zatražio podsjetnik o pojedinostima vašeg računa za {{SITENAME}}\n($4). Sljedeći {{PLURAL:$3|račun suradnika je|računi suradnika su}} povezani s ovom e-mail adresom:\n\n$2\n\n{{PLURAL:$3|Ova privremena lozinka|Ove privremene lozinke}} će isteći u {{PLURAL:$5|jedan dan|$5 dana}}.\nTrebate se prijaviti i odabrati novu lozinku. Ukoliko je netko drugi napravio ovaj\nzahtjev, ili ako ste sjeti Vaše izvorne lozinke, a vi je više ne želite promijeniti, \nmožete zanemariti ovu poruku i nastavite koristiti staru lozinku.",
        "passwordreset-emailelement": "Suradničko ime: \n$1\n\nPrivremena lozinka: \n$2",
        "passwordreset-emailsentemail": "Ako je ova adresa povezana s Vašim suradničkim računom, na nju će biti poslan podsjetnik na zaporku.",
-       "passwordreset-emailsent-capture": "Poslan Vam je podsjetnik kao e-pošta (tekst je prikazan dolje).",
-       "passwordreset-emailerror-capture": "Napravljena je e-poruka za ponovno postavljanje zaporke (prikazana ispod), ali njeno slanje suradniku nije uspjelo: $1",
        "changeemail": "Promijeni ili izbriši e-mail adresu",
        "changeemail-header": "Promijeni adresu e-pošte računa",
        "changeemail-no-info": "Morate biti prijavljeni da biste izravno pristupili ovoj stranici.",
        "minoredit": "Ovo je manja promjena",
        "watchthis": "Prati ovu stranicu",
        "savearticle": "Sačuvaj stranicu",
+       "publishpage": "Objavi stranicu",
+       "publishchanges": "Objavi izmjene",
        "preview": "Pregled kako će stranica izgledati",
        "showpreview": "Prikaži kako će izgledati",
        "showdiff": "Prikaži promjene",
        "undo-norev": "Izmjena nije mogla biti uklonjena jer ne postoji ili je obrisana.",
        "undo-nochange": "Čini se da je uređivanje već otkazano.",
        "undo-summary": "uklanjanje izmjene $1 {{GENDER:$2|suradnika|suradnice}} [[Posebno:Doprinosi/$2|$2]] ([[Razgovor sa suradnikom:$2|razgovor]])",
-       "cantcreateaccounttitle": "Nije moguće stvoriti suradnički račun",
        "cantcreateaccount-text": "Otvaranje suradničkog računa ove IP adrese ('''$1''') blokirao/la je [[User:$3|$3]].\n\nRazlog koji je dao/la $3 je ''$2''",
        "viewpagelogs": "Vidi evidencije za ovu stranicu",
        "nohistory": "Ova stranica nema starijih izmjena.",
index b2daf38..007eada 100644 (file)
        "passwordreset-emailtext-user": "Wužiwar $1 na {{GRAMMAR:lokatiw|{{SITENAME}}}} je anulowanje twojeho hesła za {{GRAMMAR:akuzatiw|{{SITENAME}}}} požadał ($4).  {{PLURAL:$3|Slědowace wužiwarske konto je|Slědowacej wužiwarskej konće stej|Slědowace wužiwarske konta su}} z tutej e-mejlowej adresu {{PLURAL:$3|zwjazane|zwjazanej|zwjazane}}:\n\n$2\n\n{{PLURAL:$3|Tute nachwilne hesło spadnje|Tutej nachwilnej hesle spadnjetej|Tute nachwilne hesła spadnu}} za {{PLURAL:$5|jedyn dźeń|$5 dnjej|$5 dny|$5 dnjow}}.\nTy měł so nětko přizjewić a nowe hesło wubrać. Jeli něchtó druhi je tute naprašowanje pósłał, abo jeli sy so zaso na prěnjotne hesło dopomnił a wjace nochceš jo změnić, móžeš tutu zdźělenku ignorować a swoje stare hesło dale wužiwać.",
        "passwordreset-emailelement": "Wužiwarske mjeno: \n$1\n\nNachwilne hesło: \n$2",
        "passwordreset-emailsentemail": "Jeli tuta e-mejlowa adresa je z wašim kontom zwjazana, so mejlka za wróćostajenje hesła pósćele.",
-       "passwordreset-emailsent-capture": "E-mejl za anulowanje hesła je so pósłała, kotraž so deleka pokazuje.",
-       "passwordreset-emailerror-capture": "E-mejl za anulowanje hesła je so wutworiła, kotraž so deleka pokazuje, ale słanje {{GENDER:$2|wužiwarjej|wužiwarce}} je so njeporadźiło: $1",
        "changeemail": "E-mejlowu adresu změnić abo wotstronić",
        "changeemail-header": "Wupjelń tutón formular, zo by swoju e-mejlowu adresu změnił. Jeli chceš zwisk e-mejloweje adresy ze swijim kontom wotstronić,  wostaj polo e-mejloweje adresy prózdne, hdyž formular preč sćeleš.",
        "changeemail-no-info": "Dyrbiš so přizjewić, zo by direktny přistup na tutu stronu měł.",
        "minoredit": "Snadna změna",
        "watchthis": "Stronu wobkedźbować",
        "savearticle": "Stronu składować",
+       "publishpage": "Stronu wozjewić",
+       "publishchanges": "Změny wozjewić",
        "preview": "Přehlad",
        "showpreview": "Přehlad pokazać",
        "showdiff": "Změny pokazać",
        "undo-nochange": "Zda so, zo změna je so hižo cofnyła.",
        "undo-summary": "Změna $1 [[Special:Contributions/$2|$2]] ([[User talk:$2|diskusija]]) bu cofnjena.",
        "undo-summary-username-hidden": "Změna $1 schowaneho wužiwarja je so anulowała",
-       "cantcreateaccounttitle": "Wužiwarske konto njeda so wutworić.",
        "cantcreateaccount-text": "Wutworjenje wužiwarskeho konta z IP-adresy '''$1''' bu wot [[User:$3|$3]] zablokowane.\n\nPřičina za blokowanje, podata wot $3, je: ''$2''",
        "cantcreateaccount-range-text": "Załoženje kontow z IP-adresow we wobłuku '''$1'', kotryž twoju IP-adresu wobsahuje (<strong>$4</strong>), je so wot [[User:$3|$3]] zablokowało.\n\nPřičina podata wot $3 je <em>$2</em>",
        "viewpagelogs": "protokole tuteje strony pokazać",
index 75ef088..17df2d7 100644 (file)
        "parser-template-recursion-depth-warning": "Limit depase pou kantite fwa yon modèl ka rele tèt li ($1)",
        "language-converter-depth-warning": "Limit sou pwofondè konvètisè lang yo depase ($1)",
        "undo-summary": "Revoke revizyon $1 ki te fèt pa [[Special:Contributions/$2|$2]] ([[User talk:$2|diskite]])",
-       "cantcreateaccounttitle": "Ou pa kapab kreye yon kont.",
        "viewpagelogs": "gade jounal paj sa a",
        "nohistory": "Istorik pou paj sa pa egziste ditou.",
        "currentrev": "Vèsyon kounye a",
index c0acf2e..9ad03b8 100644 (file)
        "password-change-forbidden": "Nem módosíthatod a jelszót ezen a wikin.",
        "externaldberror": "Hiba történt a külső adatbázis hitelesítése közben, vagy nem vagy jogosult a külső fiókod frissítésére.",
        "login": "Bejelentkezés",
+       "login-security": "Személyazonosságod igazolása",
        "nav-login-createaccount": "Bejelentkezés / fiók létrehozása",
        "userlogin": "Bejelentkezés / fiók létrehozása",
        "userloginnocreate": "Bejelentkezés",
        "userlogin-resetpassword-link": "Elfelejtetted a jelszavad?",
        "userlogin-helplink2": "Segítség a bejelentkezéshez",
        "userlogin-loggedin": "Már be vagy jelentkezve mint {{GENDER:$1|$1}}. Ha más néven akarsz belépni, alább megteheted.",
+       "userlogin-reauth": "Újra be kell jelentkezned, hogy igazold, te vagy $1.",
        "userlogin-createanother": "Másik felhasználói fiók létrehozása",
        "createacct-emailrequired": "E-mail cím",
        "createacct-emailoptional": "E-mail cím (opcionális)",
        "createacct-reason-ph": "Miért hozol létre egy másik fiókot",
        "createacct-submit": "Felhasználói fiók létrehozása",
        "createacct-another-submit": "Fiók létrehozása",
+       "createacct-continue-submit": "Fiók létrehozásának folytatása",
+       "createacct-another-continue-submit": "Fiók létrehozásának folytatása",
        "createacct-benefit-heading": "A(z) {{SITENAME}}-t hozzád hasonló emberek készítik.",
        "createacct-benefit-body1": "{{PLURAL:$1|szerkesztés|szerkesztés}}",
        "createacct-benefit-body2": "{{PLURAL:$1|lap|lap}}",
        "nocookiesnew": "A felhasználói fiókod létrejött, de nem vagy bejelentkezve. A wiki sütiket („cookie”) használ a szerkesztők azonosítására. Nálad ezek le vannak tiltva. Kérlek, engedélyezd őket a böngésződben, majd lépj be az új azonosítóddal és jelszavaddal.",
        "nocookieslogin": "A wiki sütiket („cookie”) használ a szerkesztők azonosításhoz.\nNálad ezek le vannak tiltva.\nEngedélyezd őket a böngésződben, majd próbáld újra.",
        "nocookiesfornew": "A felhasználói fiók nem lett létrehozva, mivel nem sikerült megerősítenünk a forrását.\nEllenőrizd, hogy a sütik engedélyezve vannak-e, majd frissítsd az oldalt, és próbálkozz újra.",
+       "createacct-loginerror": "A fiók sikeresen létrejött, de nem tudtál automatikusan bejelentkezni. Kérjük, [[Special:UserLogin|jelentkezz be manuálisan]]!",
        "noname": "Érvénytelen szerkesztőnevet adtál meg.",
        "loginsuccesstitle": "Sikeres bejelentkezés",
        "loginsuccess": "'''Sikeresen bejelentkeztél a(z) {{SITENAME}} wikibe „$1” néven.'''",
        "passwordreset-emailelement": "Felhasználónév: \n$1\n\nIdeiglenes jelszó: \n$2",
        "passwordreset-emailsentemail": "Ha ez az e-mail-cím van a fiókodhoz társítva, egy jelszó-visszaállító e-mailt küldünk.",
        "passwordreset-emailsentusername": "Ha ehhez a felhasználónévhez tartozik e-mail cím, akkor egy jelszó-visszaállító levelet küld a rendszer.",
-       "passwordreset-emailsent-capture": "Az alább látható jelszó-visszaállító e-mail lett elküldve.",
-       "passwordreset-emailerror-capture": "A jelszó-visszaállító e-mail generálása megtörtént, mint az alább látszik, de elküldése a {{GENDER:$2|szerkesztőnek}} nem sikerült: $1",
+       "passwordreset-emailsent-capture2": "A jelszóvisszaállító {{PLURAL:$1|e-mailt|e-maileket}} elküldtük. A felhasználói {{PLURAL:$1|név és a jelszó|nevek és jelszavak listája}} lentebb látható.",
        "passwordreset-invalideamil": "Érvénytelen e-mail cím",
        "changeemail": "E-mail cím megváltoztatása vagy eltávolítása",
        "changeemail-header": "Töltsd ki ezt az űrlapot az e-mail-címed megváltoztatásához. Ha nem szeretnél semmilyen e-mail-címet kapcsolni a fiókodhoz, hagyd üresen az új e-mail-cím mezőjét az űrlap elküldésekor.",
-       "changeemail-passwordrequired": "Meg kell adnod a jelszavadat ennek a változtatásnak a végrehajtásához.",
        "changeemail-no-info": "A lap közvetlen eléréséhez be kell jelentkezned.",
        "changeemail-oldemail": "Jelenlegi e-mail-cím:",
        "changeemail-newemail": "Új e-mail-cím:",
        "undo-nochange": "A szerkesztés már vissza lett állítva.",
        "undo-summary": "Visszavontam [[Special:Contributions/$2|$2]] ([[User talk:$2|vita]]) szerkesztését (oldid: $1)",
        "undo-summary-username-hidden": "A rejtett felhasználó által végzett $1 változat visszavonása",
-       "cantcreateaccounttitle": "Felhasználói fiók létrehozása sikertelen",
        "cantcreateaccount-text": "Erről az IP-címről ('''$1''') nem lehet regisztrálni, mert [[User:$3|$3]] blokkolta az alábbi indokkal:\n\n:''$2''",
        "cantcreateaccount-range-text": "A regisztrációt a(z) <strong>$1</strong> IP-címtartományban, amelybe a te IP-címed (<strong>$4</strong>) is tartozik, [[User:$3|$3]] blokkolta.",
        "viewpagelogs": "A lap a rendszernaplókban",
        "userrights-changeable-col": "Megváltoztatható csoportok",
        "userrights-unchangeable-col": "Nem megváltoztatható csoportok",
        "userrights-conflict": "Felhasználói jogok ütközése! Kérlek, végezd el újra a változtatásokat.",
-       "userrights-removed-self": "Sikeresen eltávolítottad a saját jogosultságaidat, így már nem tudod elérni ezt az oldalt.",
+       "userrights-removed-self": "Eltávolítottad a saját jogosultságaidat, így már nem tudod elérni ezt az oldalt.",
        "group": "Csoport:",
        "group-user": "szerkesztők",
        "group-autoconfirmed": "automatikusan megerősített szerkesztők",
        "right-override-export-depth": "Lapok exportálása a hivatkozott lapokkal együtt, legfeljebb 5-ös mélységig",
        "right-sendemail": "e-mail küldése más felhasználóknak",
        "right-passwordreset": "Jelszó visszaállítási emailek megtekintése",
-       "right-managechangetags": "[[Special:Tags|címkék]] létrehozása és törlése az adatbázisban",
+       "right-managechangetags": "[[Special:Tags|címkék]] létrehozása és (de)aktiválása",
        "right-applychangetags": "[[Special:Tags|címkék]] alkalmazása a változakra",
        "right-changetags": "egyedi lapváltozatokon és naplóbejegyzéseken tetszőleges [[Special:Tags|címkék]] hozzáadása és törlése",
        "right-deletechangetags": "[[Special:Tags|Címkék]] törlése az adatbázisból",
        "rightslogtext": "Ez a rendszernapló a felhasználó jogosultságok változásait mutatja.",
        "action-read": "lap olvasása",
        "action-edit": "lap szerkesztése",
-       "action-createpage": "új lap készítése",
-       "action-createtalk": "vitalap készítése",
+       "action-createpage": "ennek a lapnak a létrehozása",
+       "action-createtalk": "vitalap létrehozása",
        "action-createaccount": "felhasználói fiók elkészítése",
        "action-history": "laptörténet megtekintése",
        "action-minoredit": "szerkesztés aprónak jelölése",
        "action-viewmyprivateinfo": "személyes adatok megtekintése",
        "action-editmyprivateinfo": "személyes adatok szerkesztése",
        "action-editcontentmodel": "a lap tartalom modelljének szerkesztése",
-       "action-managechangetags": "adatbázis címkék létrehozása és törlése",
+       "action-managechangetags": "adatbáziscímkék létrehozása és (de)aktiválása",
        "action-applychangetags": "változtatások címkézése",
        "action-changetags": "egyedi változtatások és napló bejegyzések tetszőleges címkével való ellátása és törlése",
        "action-deletechangetags": "címkék törlése az adatbáziból",
+       "action-purge": "oldal gyorsítótárának ürítése",
        "nchanges": "$1 változtatás",
        "enhancedrc-since-last-visit": "$1 az utolsó látogatás óta",
        "enhancedrc-history": "történet",
        "recentchanges-page-added-to-category": "[[:$1]] hozzáadva a kategóriához",
        "recentchanges-page-added-to-category-bundled": "[[:$1]] hozzáadva a kategóriához, [[Special:WhatLinksHere/$1|ez a lap be van illesztve más lapokra]]",
        "recentchanges-page-removed-from-category": "[[:$1]] eltávolítva a kategóriából",
-       "recentchanges-page-removed-from-category-bundled": "[[:$1]] és {{PLURAL:$2|egy oldal|$2 oldal}} eltávolítva a kategóriából",
+       "recentchanges-page-removed-from-category-bundled": "[[:$1]] eltávolítva a kategóriából, [[Special:WhatLinksHere/$1|ez a lap be van illesztve más lapokra]]",
        "upload": "Fájl feltöltése",
        "uploadbtn": "Fájl feltöltése",
        "reuploaddesc": "Visszatérés a feltöltési űrlaphoz.",
        "uploaded-script-svg": "A feltöltött SVG fájlodban szkriptelemet találtunk: \"$1\".",
        "uploaded-hostile-svg": "Nem biztonságos CSS kódot találtunk a feltöltött SVG fájlod stíluselemei között.",
        "uploaded-event-handler-on-svg": "Az alábbi eseménykezelő-attribútum beállítása nem megengedett az SVG fájlokban: <code>$1=$2</code>.",
-       "uploaded-href-unsafe-target-svg": "Nem biztonságos célra mutató href-et találtam a feltöltött SVG fájlban: <code>&lt;$1 $2=\"$3\"&gt;</code>.",
+       "uploaded-href-unsafe-target-svg": "Nem biztonságos adatra mutató href-et találtunk a feltöltött SVG-fájlban: URI-cél <code>&lt;$1 $2=\"$3\"&gt;</code>.",
        "uploaded-animate-svg": "A feltöltött SVG fájlban \"animate\" taget találtam, ami az alábbi \"from\" attribútumával megváltoztathat egy href-et: <code>&lt;$1 $2=\"$3\"&gt;</code>.",
        "uploaded-setting-handler-svg": "Az SVG kódok, amelyek a \"handler\" attribútumot távolra/adatra/szkriptre állítják, le vannak tiltva. A feltöltött SVG fájlban a következőt találtam: <code>$1=\"$2\"</code>.",
        "uploaded-remote-url-svg": "Az SVG kódok, amelyek bármely stílus-attribútumot távoli URL-ra állítják, le vannak tiltva. A feltöltött SVG fájlban a következőt találtam: <code>$1=\"$2\"</code>.",
index 214d0b1..bcb0af0 100644 (file)
        "cannotlogoutnow-title": "Impossibile clauder session ora",
        "cannotlogoutnow-text": "Non es possibile clauder le session usante $1.",
        "welcomeuser": "Benvenite, $1!",
-       "welcomecreation-msg": "Tu conto ha essite create.\nNon oblida personalisar tu [[Special:Preferences|preferentias in {{SITENAME}}]].",
+       "welcomecreation-msg": "Tu conto ha essite create.\nTu pote personalisar tu [[Special:Preferences|preferentias]] in {{SITENAME}}, si tu vole.",
        "yourname": "Nomine de usator:",
        "userlogin-yourname": "Nomine de usator",
        "userlogin-yourname-ph": "Entra tu nomine de usator",
        "passwordreset-emailelement": "Nomine de usator: \n$1\n\nContrasigno temporari: \n$2",
        "passwordreset-emailsentemail": "Si iste adresse es associate a tu conto, alora un e-mail pro reinitialisar le contrasigno essera inviate.",
        "passwordreset-emailsentusername": "Si il ha un adresse de e-mail associate a iste conto, alora un e-mail pro reinitialisar le contrasigno essera inviate.",
-       "passwordreset-emailsent-capture": "Un message de e-mail pro le reinitialisation del contrasigno ha essite inviate; iste message es monstrate hic infra.",
-       "passwordreset-emailerror-capture": "Un e-mail pro le reinitialisation del contrasigno ha essite generate; iste message es monstrate hic infra, ma le invio al {{GENDER:$2|usator}} ha fallite: $1",
        "passwordreset-emailsent-capture2": "Le {{PLURAL:$1|message|messages}} de e-mail pro reinitialisation de contrasigno ha essite inviate. Le {{PLURAL:$1|nomine de usator e contrasigno|lista de nomines de usator e contrasignos}} appare hic infra.",
        "passwordreset-emailerror-capture2": "Le invio de e-mail al {{GENDER:$2|usator}} ha fallite: $1 Le {{PLURAL:$3|nomine de usator e contrasigno|lista de nomines de usator e contrasignos}} appare hic infra.",
        "passwordreset-nocaller": "Un appellator debe esser fornite",
        "passwordreset-nodata": "Ni un nomine de usator ni un adresse de e-mail ha essite fornite",
        "changeemail": "Cambiar o remover adresse de e-mail",
        "changeemail-header": "Completa iste formulario pro cambiar tu adresse de e-mail. Si tu vole remover le association de omne adresse de e-mail ab tu conto, lassa le campo pro le nove adresse de e-mail vacue quando tu submitte le formulario.",
-       "changeemail-passwordrequired": "Essera necessari entrar tu contrasigno pro confirmar iste cambiamento.",
        "changeemail-no-info": "Tu debe aperir un session pro poter acceder directemente a iste pagina.",
        "changeemail-oldemail": "Adresse de e-mail actual:",
        "changeemail-newemail": "Adresse de e-mail nove:",
        "undo-nochange": "Pare que iste modification ha jam essite disfacite.",
        "undo-summary": "Annullava le version $1 per [[Special:Contributions/$2|$2]] ([[User talk:$2|Discussion]] | [[Special:Contributions/$2|{{MediaWiki:Contribslink}}]])",
        "undo-summary-username-hidden": "Disfacer le revision $1 facite per un usator celate",
-       "cantcreateaccounttitle": "Non pote crear conto",
        "cantcreateaccount-text": "Le creation de contos desde iste adresse IP ('''$1''') ha essite blocate per [[User:$3|$3]].\n\nLe motivo que $3 dava es ''$2''",
        "cantcreateaccount-range-text": "Le creation de contos ab le adresses IP in le intervallo <strong>$1</strong>, le qual include tu adresse IP (<strong>$4</strong>), ha essite blocate per [[User:$3|$3]].\n\nLe motivo fornite per $3 es <em>$2</em>",
        "viewpagelogs": "Vider le entratas del registro pro iste pagina",
        "uploadstash-errclear": "Le radimento del files ha fallite.",
        "uploadstash-refresh": "Refrescar le lista de files",
        "uploadstash-thumbnail": "vider miniatura",
+       "uploadstash-exception": "Impossibile immagazinar le incargamento in le reserva ($1): \"$2\".",
        "invalid-chunk-offset": "Position de segmento invalide",
        "img-auth-accessdenied": "Accesso refusate",
        "img-auth-nopathinfo": "PATH_INFO manca.\nLe servitor non ha essite configurate pro passar iste information.\nIllo pote esser basate super CGI e non pote supportar img_auth.\nVide https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization.",
        "watchnologin": "Tu non ha aperite un session",
        "addwatch": "Adder al observatorio",
        "addedwatchtext": "Le pagina \"[[:$1]]\", e su pagina de discussion, ha essite addite a [[Special:Watchlist|tu observatorio]].",
+       "addedwatchtext-talk": "\"[[:$1]]\" e su pagina associate ha essite addite a tu [[Special:Watchlist|observatorio]].",
        "addedwatchtext-short": "Le pagina \"$1\" ha essite addite a tu observatorio.",
        "removewatch": "Remover del observatorio",
        "removedwatchtext": "Le pagina \"[[:$1]]\", e su pagina de discussion, ha essite removite de [[Special:Watchlist|tu observatorio]].",
+       "removedwatchtext-talk": "\"[[:$1]]\" e su pagina associate ha essite removite de tu [[Special:Watchlist|observatorio]].",
        "removedwatchtext-short": "Le pagina \"$1\" ha essite removite de tu observatorio.",
        "watch": "Observar",
        "watchthispage": "Observar iste pagina",
        "protect_expiry_invalid": "Le tempore de expiration es invalide.",
        "protect_expiry_old": "Le tempore de expiration es in le passato.",
        "protect-unchain-permissions": "Disblocar ulterior optiones de protection",
-       "protect-text": "In basso tu pote vider e modificar le nivello de protection del pagina '''$1'''.",
-       "protect-locked-blocked": "Tu non pote cambiar le nivellos de protection durante que tu es blocate.\nEcce le configurationes actual del pagina '''$1''':",
-       "protect-locked-dblock": "Le nivellos de protection non pote esser cambiate proque es active un blocada del base de datos.\nEcce le configurationes actual del pagina '''$1''':",
+       "protect-text": "Hic tu pote vider e cambiar le nivello de protection del pagina <strong>$1</strong>.",
+       "protect-locked-blocked": "Tu non pote cambiar le nivellos de protection durante que tu es blocate.\nEcce le configuration actual del pagina <strong>$1</strong>:",
+       "protect-locked-dblock": "Le nivellos de protection non pote esser cambiate perque le base de datos es blocate.\nEcce le configuration actual del pagina <strong>$1</strong>:",
        "protect-locked-access": "Tu conto non ha le permission de cambiar le nivellos de protection de paginas.\nEcce le configurationes actual del pagina '''$1''':",
        "protect-cascadeon": "Iste pagina es actualmente protegite proque illo es transcludite in le sequente {{PLURAL:$1|pagina, le qual|paginas, le quales}} ha activate le protection in cascada.\nCambiamentos in le nivello de protection de iste pagina non influentia le protection in cascada.",
        "protect-default": "Permitter a tote le usatores",
        "undeletehistorynoadmin": "Iste pagina ha essite delite.\nLe motivo del deletion se monstra in le summario infra, con le detalios del usatores que habeva modificate iste pagina ante le deletion.\nLe texto complete de iste versiones delite es solmente disponibile al administratores.",
        "undelete-revision": "Version delite de $1 (facite le $4 a $5) per $3:",
        "undeleterevision-missing": "Version invalide o mancante.\nEs possibile que le adresse URL es invalide, o que le version ha essite restaurate o eliminate del archivo.",
+       "undeleterevision-duplicate-revid": "{{PLURAL:$1|Un version|$1 versiones}} non poteva esser restaurate, perque {{PLURAL:$1|su|lor}} <code>rev_id</code> esseva jam in uso.",
        "undelete-nodiff": "Nulle version precedente trovate.",
        "undeletebtn": "Restaurar",
        "undeletelink": "vider/restaurar",
        "undeletecomment": "Motivo:",
        "undeletedrevisions": "{{PLURAL:$1|1 version|$1 versiones}} restaurate",
        "undeletedrevisions-files": "{{PLURAL:$1|1 version|$1 versiones}} e {{PLURAL:$2|1 file|$2 files}} restaurate",
-       "undeletedfiles": "$1 {{PLURAL:$1|archivo|archivos}} restaurate",
-       "cannotundelete": "Le restauration ha fallite:\n$1",
+       "undeletedfiles": "$1 {{PLURAL:$1|file|files}} restaurate",
+       "cannotundelete": "Le restauration ha partial- o totalmente fallite:\n$1",
        "undeletedpage": "'''$1 ha essite restaurate'''\n\nConsulta le [[Special:Log/delete|registro de deletiones]] pro un lista de deletiones e restaurationes recente.",
        "undelete-header": "Vide [[Special:Log/delete|le registro de deletiones]] pro un lista de paginas recentemente delite.",
        "undelete-search-title": "Cercar in paginas delite",
        "anoncontribs": "Contributiones",
        "contribsub2": "Pro {{GENDER:$3|$1}} ($2)",
        "contributions-userdoesnotexist": "Le conto de usator \"$1\" non es registrate.",
-       "nocontribs": "Necun modification ha essite trovate secundo iste criterios.",
+       "nocontribs": "Nulle modification correspondente a iste criterios ha essite trovate.",
        "uctop": "(ultime)",
        "month": "A partir del mense (e anterior):",
        "year": "A partir del anno (e anterior):",
        "sp-contributions-newbies-sub": "Pro nove contos",
        "sp-contributions-newbies-title": "Contributiones de nove contos de usator",
        "sp-contributions-blocklog": "Registro de blocadas",
-       "sp-contributions-suppresslog": "contributiones supprimite de usatores",
-       "sp-contributions-deleted": "contributiones delite de usatores",
+       "sp-contributions-suppresslog": "contributiones supprimite del {{GENDER:$1|usator}}",
+       "sp-contributions-deleted": "contributiones delite del {{GENDER:$1|usator}}",
        "sp-contributions-uploads": "incargamentos",
        "sp-contributions-logs": "registros",
        "sp-contributions-talk": "discussion",
        "ipb-blocklist": "Vider blocadas existente",
        "ipb-blocklist-contribs": "Contributiones de {{GENDER:$1|$1}}",
        "ipb-blocklist-duration-left": "$1 restante",
-       "unblockip": "Disblocar adresse IP",
-       "unblockiptext": "Usa le formulario infra pro restaurar le accesso de scriptura\na un adresse IP blocate previemente.",
+       "unblockip": "Disblocar usator",
+       "unblockiptext": "Usa le formulario infra pro restaurar le accesso de scriptura a un adresse IP o nomine de usator blocate previemente.",
        "ipusubmit": "Cancellar iste blocada",
-       "unblocked": "[[User:$1|$1]] ha essite disblocate",
+       "unblocked": "[[User:$1|$1]] ha essite disblocate.",
        "unblocked-range": "$1 ha essite disblocate",
-       "unblocked-id": "Le blocada $1 ha essite eliminate",
+       "unblocked-id": "Le blocada $1 ha essite removite.",
        "unblocked-ip": "[[Special:Contributions/$1|$1]] ha essite disblocate.",
        "blocklist": "Usatores blocate",
        "ipblocklist": "Usatores blocate",
        "locknoconfirm": "Tu non ha marcate le quadrato de confirmation.",
        "lockdbsuccesssub": "Base de datos blocate con successo",
        "unlockdbsuccesssub": "Base de datos disblocate con successo",
-       "lockdbsuccesstext": "Le base de datos de {{SITENAME}} ha essite blocate.\n<br />Rememora te de disblocar lo post completar tu mantenentia.",
-       "unlockdbsuccesstext": "Le base de datos de {{SITENAME}} ha essite disblocate.",
+       "lockdbsuccesstext": "Le base de datos ha essite blocate.<br />\nNon oblida de [[Special:UnlockDB|disblocar lo]] post haber terminate le mantenentia.",
+       "unlockdbsuccesstext": "Le base de datos ha essite disblocate.",
        "lockfilenotwritable": "Impossibile scriber al file de blocada del base de datos.\nPro blocar o disblocar le base de datos, le servitor web debe poter scriber a iste file.",
        "databaselocked": "Le base de datos es jam blocate.",
        "databasenotlocked": "Le base de datos non es blocate.",
        "movenologintext": "Tu debe esser un usator registrate e [[Special:UserLogin|aperir un session]] pro poter renominar un pagina.",
        "movenotallowed": "Tu non ha le permission de renominar paginas.",
        "movenotallowedfile": "Tu non ha le permission de renominar files.",
-       "cant-move-user-page": "Tu non ha le permission de renominar paginas principal de usatores.",
+       "cant-move-user-page": "Tu non ha le permission de renominar paginas de usator (excepte subpaginas).",
        "cant-move-to-user-page": "Tu non ha le permission de renominar un pagina verso un pagina de usator (excepte un subpagina de usator).",
        "cant-move-category-page": "Tu non ha le permission de renominar paginas de categoria.",
        "cant-move-to-category-page": "Tu non ha le permission de renominar un pagina in un pagina de categoria.",
        "table_pager_empty": "Nulle resultato",
        "autosumm-blank": "Pagina vacuate",
        "autosumm-replace": "Contento reimplaciate per '$1'",
-       "autoredircomment": "Redirection verso [[$1]]",
+       "autoredircomment": "Pagina redirigite verso [[$1]]",
        "autosumm-new": "Pagina create con '$1'",
        "autosumm-newblank": "Pagina vacue create",
        "lag-warn-normal": "Le modificationes plus nove que $1 {{PLURAL:$1|secunda|secundas}} possibilemente non se revela in iste lista.",
index 1e7af01..bc271bd 100644 (file)
@@ -47,7 +47,8 @@
                        "Arief",
                        "Nemo bis",
                        "Mbrt",
-                       "Beeyan"
+                       "Beeyan",
+                       "Bonaditya"
                ]
        },
        "tog-underline": "Garis bawahi pranala:",
        "passwordreset-emailelement": "Nama pengguna: \n$1\n\nSandi sementara: \n$2",
        "passwordreset-emailsentemail": "Jika alamat surel ini berkaitan dengan akun Anda, maka surel untuk menyetel ulang kata sandi akan dikirim.",
        "passwordreset-emailsentusername": "Jika ada alamat surel yang berkaitan dengan nama pengguna ini, maka surel untuk menyetel ulang kata sandi akan dikirim.",
-       "passwordreset-emailsent-capture": "Surel setel ulang kata sandi telah dikirim, yang ditampilkan di bawah.",
-       "passwordreset-emailerror-capture": "Surel setel ulang kata sandi telah dibuat, yang ditampilkan di bawah, namun pengiriman pada {{GENDER:$2|pengguna}} gagal: $1",
        "passwordreset-emailsent-capture2": "Pemulihan kata sandi {{PLURAL:$1|surel|surel}} telah dikirim. {{PLURAL:$1|Nama pengguna dan kata sandi|Daftar nama pengguna dan kata sandi}} ditampilkan di bawah.",
        "passwordreset-emailerror-capture2": "Pengiriman surel kepada {{GENDER:$2|pengguna}} gagal: $1 {{PLURAL:$3|Nama pengguna dan kata sandi|Daftar nama pengguna dan kata sandi}} ditampilkan di bawah.",
        "passwordreset-nocaller": "Pemanggil harus diberikan",
        "passwordreset-nodata": "Nama pengguna ataupun alamat surel tidak diberikan",
        "changeemail": "Ubah atau hapus alamat surel",
        "changeemail-header": "Lengkapi formulir ini untuk mengubah alamat surel Anda. Jika Anda ingin menghapus seluruh alamat surel yang berkaitan dengan akun Anda, kosongkan alamat surel ketika mengirim formulir.",
-       "changeemail-passwordrequired": "Anda diharuskan memasukkan kata sandi untuk mengonfirmasikan perubahan ini.",
        "changeemail-no-info": "Anda harus masuk log untuk mengakses halaman ini secara langsung.",
        "changeemail-oldemail": "Alamat surel saat ini:",
        "changeemail-newemail": "Alamat surel baru:",
        "undo-nochange": "Suntingan ini nampaknya telah dibatalkan.",
        "undo-summary": "Membalikkan revisi $1 oleh [[Special:Contributions/$2|$2]] ([[User talk:$2|bicara]])",
        "undo-summary-username-hidden": "Batalkan revisi $1 oleh seorang pengguna tersembunyi",
-       "cantcreateaccounttitle": "Akun tak dapat dibuat",
        "cantcreateaccount-text": "Pembuatan akun dari alamat IP ini (<strong>$1</strong>) telah diblokir oleh [[User:$3|$3]].\n\nAlasan yang diberikan oleh $3 adalah ''$2''",
        "cantcreateaccount-range-text": "Pembuatan akun dari alamat IP dalam rentang <strong>$1</strong>, yang mencakup alamat IP anda (<strong>$4</strong>), telah diblokir oleh [[User:$3|$3]].\n\nAlasan yang diberikan oleh  $3  adalah <em>$2</em>",
        "viewpagelogs": "Lihat log halaman ini",
        "mw-widgets-dateinput-placeholder-month": "TTTT-BB",
        "mw-widgets-titleinput-description-new-page": "halaman belum ada",
        "mw-widgets-titleinput-description-redirect": "mengalihkan ke $1",
-       "api-error-blacklisted": "Pilih judul lain yang deskriptif",
        "sessionmanager-tie": "Tidak dapat menggabungkan banyak jenis otentikasi permintaan: $1.",
        "sessionprovider-generic": "sesi $1",
        "sessionprovider-mediawiki-session-cookiesessionprovider": "sesi berdasarkan kuki",
index b585c93..8d570ec 100644 (file)
        "passwordreset-emailelement": "Nagan ti agar-aramat: \n$1\n\nTemporario a kontrasenias: \n$2",
        "passwordreset-emailsentemail": "No daytoy nga adres ti esurat ket mainaig iti pakabilangam, maipatulodto ti maysa nga esurat iti panangisaad manen ti kontrasenias.",
        "passwordreset-emailsentusername": "No adda adres ti esurat a mainaig iti daytoy a nagan ti agar-aramat, addanto maipatulod nga esurat iti panangisaad manen ti kontrasenia.",
-       "passwordreset-emailsent-capture": "Ti maysa nga esurat ti panangisaad manen ti kontrasenias ket naipatuloden, a naipakita dita baba.",
-       "passwordreset-emailerror-capture": "Naaramid ti maysa nga esurat a panangisaad manen ti kontrasenias, a napaikita dita baba, ngem ti panangitulod kenni {{GENDER:$2|agar-aramat}} ket napaay: $1",
        "changeemail": "Sukatan wenno ikkaten ti adres ti esurat",
        "changeemail-header": "Kompletuen daytoy a porma tapno masukatan ti adres ti esuratmo. No kayatmo a maikkat ti pannakainaig iti ania man nga adres ti esurat manipud iti pakabilangam, ibati a blanko ti baro nga adres ti esurat no ited ti porma.",
-       "changeemail-passwordrequired": "Masapulmonto nga ikabil ti kontraseniasmo tapno mapasingkedan daytoy a panagbaliw.",
        "changeemail-no-info": "Masapul a nakastrekka tapno dagus a makapan iti ditoy a panid.",
        "changeemail-oldemail": "Agdama nga esurat a pagtaengan:",
        "changeemail-newemail": "Baro nga esurat a pagtaengan:",
        "undo-nochange": "Ti inurnos ket kasla naibabawin.",
        "undo-summary": "Ibabawi ti $1 a binaliwan babaen ni [[Special:Contributions/$2|$2]] ([[User talk:$2|tungtungan]])",
        "undo-summary-username-hidden": "Isubli ti $1 a binaliwan babaen ti nailemmeng nga agar-aramat",
-       "cantcreateaccounttitle": "Saan a makapartuat iti pakabilangan",
        "cantcreateaccount-text": "Ti panagpartuat iti pakabilangan manipud ti daytoy nga IP a pagtaengan (<strong>$1</strong>) ket sinerraan babaen ni [[User:$3|$3]].\n\nTi inted a rason babaen ni $3 ket <em>$2</em>",
        "cantcreateaccount-range-text": "Ti panagpartuat iti pakabilangan manipud kadagiti pagtaengan ti IP iti sakop ti <strong>$1</strong>, a mairaman ti IP a pagtaengam (<strong>$4</strong>), ket sinerraan babaen ni [[User:$3|$3]].\n\nTi inted a rason babaen ni $3 ket <em>$2</em>",
        "viewpagelogs": "Kitaen dagiti listaan para iti daytoy a panid",
index 8048a84..a8fbc04 100644 (file)
        "passwordreset-emailelement": "Notandanafn: \n$1\n\nBráðabirgðalykilorð: \n$2",
        "passwordreset-emailsentemail": "Ef þetta netfang er skráð fyrir aðganginum þínum þá hefur töluvpóstur verið sendur til að endursetja lykilorðið.",
        "passwordreset-emailsentusername": "Ef eitthvað netfang er skráð fyrir aðganginum þínum, þá mun verða sendur töluvpóstur til að endursetja lykilorðið.",
-       "passwordreset-emailsent-capture": "Tölvupóstur til að endursetja lykilorðið hefur verið sendur í tölvupósti, sem er sýndur hér fyrir neðan.",
-       "passwordreset-emailerror-capture": "Tölvupóstur til að endursetja lykilorðið var búinn til, sem er sýndur hér fyrir neðan, en ekki tókst að senda hana til {{GENDER:$2|notandans}}: $1",
        "changeemail": "Breyta eða fjarlægja netfang",
        "changeemail-header": "Fylltu út þetta eyðublað til að breyta netfanginu þínu. Ef þú vilt fjarlægja tengingu allra netfanga frá aðganginum þínum skildu þá netfangs reitinn eftir tóman.",
-       "changeemail-passwordrequired": "Þú verður að setja inn lykilorðið þitt til að staðfesta þessa breytingu.",
        "changeemail-no-info": "Þú verður að vera skráð(ur) inn til að hafa aðgang að þessari síðu.",
        "changeemail-oldemail": "Núverandi netfang:",
        "changeemail-newemail": "Nýtt netfang:",
        "watchthis": "Vakta þessa síðu",
        "savearticle": "Vista síðu",
        "publishpage": "Gefa út síðu",
+       "publishchanges": "Gefa út breytingar",
        "preview": "Forskoða",
        "showpreview": "Forskoða",
        "showdiff": "Sýna breytingar",
+       "blankarticle": "<strong>Viðvörun:</strong> Síðan sem þú ert að búa til er tóm.\nEf þú smellir aftur á \"{{int:savearticle}}\", verður síðan búin til án innihalds.",
        "anoneditwarning": "<strong>Viðvörun:</strong> Þú ert ekki innskráð(ur). Vistfang þitt verður sýnt opinberlega ef þú gerir einhverjar breytingar. Ef þú <strong>[$1 skráir þig inn]</strong> eða <strong>[$2 stofnar aðgang]</strong> munu breytingarnar þínar vera tengdar við notandanafn þitt, ásamt öðrum kostum.",
        "anonpreviewwarning": "Þú ert ekki innskráð(ur). Vistfang þitt skráist í breytingaskrá síðunnar.",
        "missingsummary": "'''Áminning:''' Þú hefur ekki skrifað breytingarágrip.\nEf þú smellir á Vista aftur, verður breyting þín vistuð án þess.",
        "permissionserrorstext-withaction": "Þú hefur ekki réttindi til að $2, af eftirfarandi {{PLURAL:$1|ástæðu|ástæðum}}:",
        "recreate-moveddeleted-warn": "'''Viðvörun: Þú ert að endurskapa síðu sem áður hefur verið eytt.'''\n\nAthuga skal hvort viðeigandi sé að gera þessa síðu.\nEyðingarskrá og flutningaskrá fyrir þessa síðu eru útvegaðar hér til þæginda:",
        "moveddeleted-notice": "Þessari síðu hefur verið eytt.\nEyðingaskrá og flutningaskrá síðunnar eru gefnar fyrir neðan til tilvísunar.",
+       "moveddeleted-notice-recent": "Því miður var þessari síðu eytt nýlega (innan síðustu 24 tímana).\nEyðingar og færsluskráin fyrir síðuna eru gefnar hér fyrir neðan til glöggvunar.",
        "log-fulllog": "Skoða alla aðgerðaskrána",
        "edit-hook-aborted": "Breyting síðu stöðvuð af viðbótarkrók (extension hook).\nEngin skýring gefin.",
        "edit-gone-missing": "Gat ekki uppfært síðu.\nSvo virðist sem henni hafi verið eytt.",
        "content-model-text": "hreinn texti",
        "content-model-javascript": "JavaScript",
        "content-model-css": "CSS",
+       "content-json-empty-object": "Tómur hlutur",
+       "content-json-empty-array": "Tómt fylki",
        "duplicate-args-category": "Síður sem nota tvíteknar breytur við ítengingu sniðmáts",
        "expensive-parserfunction-warning": "'''Viðvörun:''' Þessi síða inniheldur of mörg vinnslufrek aðgerðar þáttunar köll.\n\nHún ætti að innihalda minna en $2 {{PLURAL:$2|kall|köll}}, en {{PLURAL:$1|er nú $1 kall|eru nú $1 köll}}.",
        "expensive-parserfunction-category": "Síður með of mörg vinnslufrek aðgerðar þáttunar köll",
        "undo-nochange": "Breytingin virðist þegar hafa verið tekin til baka.",
        "undo-summary": "Tek aftur breytingu $1 frá [[Special:Contributions/$2|$2]] ([[User talk:$2|spjall]])",
        "undo-summary-username-hidden": "Afturkalla breytingu $1 eftir faldan notanda",
-       "cantcreateaccounttitle": "Ekki hægt að búa til aðgang",
        "cantcreateaccount-text": "Aðgangsgerð fyrir þetta vistfang ('''$1''') hefur verið bannað af [[User:$3|$3]].\n\nÁstæðan sem $3 gaf fyrir því er ''$2''",
        "cantcreateaccount-range-text": "Aðgangsgerð frá visföngunum „$1”, sem innihalda vistfang þitt („$4”) hefur verið bönnuð af [[User:$3|$3]].\n\nÁstæðan sem $3 gaf fyrir því er „$2”",
        "viewpagelogs": "Sýna aðgerðir varðandi þessa síðu",
        "revdelete-no-file": "Umbeðin skrá er ekki til.",
        "revdelete-show-file-confirm": "Ertu viss um að þú viljir sjá eydda breytingu af síðunni \"<nowiki>$1</nowiki>\" frá $2 $3?",
        "revdelete-show-file-submit": "Já",
+       "revdelete-selected-text": "{{PLURAL:$1|Valin útgáfa|Valdar útgáfur}} [[:$2]]:",
+       "revdelete-selected-file": "{{PLURAL:$1|Valin útgáfa skráarinnar|Valdar útgáfur skráarinnar}} [[:$2]]:",
        "logdelete-selected": "{{PLURAL:$1|Valin aðgerð|Valdar aðgerðir}}:",
+       "revdelete-text-text": "Eyddar breytingar munu áfram birtast í breytingarsögu, en hlutar hennar verða óaðgengileg almenningi.",
+       "revdelete-text-file": "Eyddar breytingar skráar munu áfram birtast í breytingarsögu, en hlutar hennar verða óaðgengileg almenningi.",
+       "revdelete-text-others": "Aðrir stjórnendur munu enn sjá falda efnið og geta tekið aftur eyðinguna, nema frekari takmarkanir séu í notkun.",
        "revdelete-confirm": "Staðfestu að þú viljir gera þetta, að þú skiljir afleiðingarnar og að þú sért að gera þetta í samræmi við  [[{{MediaWiki:Policy-url}}|samþykktir]].",
        "revdelete-suppress-text": "Bælingu á '''eingöngu''' að nota í eftirfarandi tilfellum:\n* Mögulegar ærumleiðandi upplýsingar\n* Óviðeigandi persónulegar upplýsingar\n*: ''heimilisfang, símanúmer, kennitala, osfrv.''",
        "revdelete-legend": "Setja sjáanlegar hamlanir",
        "search-category": "(flokkur $1)",
        "search-file-match": "(passar við innihald skráa)",
        "search-suggest": "Varstu að leita að: $1",
+       "search-rewritten": "Sýni niðurstöður $1. Leita í staðinn að $2.",
        "search-interwiki-caption": "Systurverkefni",
        "search-interwiki-default": "Útkomur frá $1:",
        "search-interwiki-more": "(fleiri)",
        "showingresultsinrange": "Sýni allt að <strong>$1</strong> {{PLURAL:$1|niðurstöðu|niðurstöður}} á bilinu <strong>$2</strong> til <strong>$3</strong>.",
        "search-showingresults": "{{PLURAL:$4|Niðurstaða|Niðurstöður}} <strong>$1-$2</strong> af <strong>$3</strong>",
        "search-nonefound": "Engar niðurstöður pössuðu við fyrirspurnina.",
+       "search-nonefound-thiswiki": "Engar niðurstöður fundust við fyrirspurninni á þessu vefsvæði.",
        "powersearch-legend": "Ítarlegri leit",
        "powersearch-ns": "Leita í nafnrýmum:",
        "powersearch-togglelabel": "Athuga:",
        "undeletedrevisions": "$1 {{PLURAL:$1|breyting endurvakin|breytingar endurvaktar}}",
        "undeletedrevisions-files": "$1 {{PLURAL:$1|breyting|breytingar}} og $2 {{PLURAL:$2|skrá|skrár}} endurvaktar",
        "undeletedfiles": "$1 {{PLURAL:$1|skrá endurvakin|skrár endurvaktar}}",
-       "cannotundelete": "Ekki var hægt að afturkalla eyðingu.\n$1",
+       "cannotundelete": "Afturköllun eyðingar mistókst að hluta eða í heild: \n$1",
        "undeletedpage": "'''$1 var endurvakin'''\n\nSkoðaðu [[Special:Log/delete|eyðingaskrána]] til að skoða eyðingar og endurvakningar.",
        "undelete-header": "Sjá [[Special:Log/delete|eyðingarskrá]] fyrir síður sem nýlega hefur verið eytt.",
        "undelete-search-title": "Leita í eyddum síðum",
        "sp-contributions-newbies-sub": "Fyrir nýliða",
        "sp-contributions-newbies-title": "Breytingar nýrra notenda",
        "sp-contributions-blocklog": "fyrri bönn",
-       "sp-contributions-suppresslog": "bæld framlög notanda",
-       "sp-contributions-deleted": "eyddar breytingar notanda",
+       "sp-contributions-suppresslog": "bæld framlög {{GENDER:$1|notanda}}",
+       "sp-contributions-deleted": "eyddar breytingar {{GENDER:$1|notanda}}",
        "sp-contributions-uploads": "innsendingar",
        "sp-contributions-logs": "aðgerðaskrá",
        "sp-contributions-talk": "spjall",
index 2a71972..c4ebf7c 100644 (file)
        "passwordreset-emailelement": "Nome utente: \n$1\n\nPassword temporanea: \n$2",
        "passwordreset-emailsentemail": "Se questo indirizzo di posta elettronica è associato con la tua utenza, allora verrà inviata una email per reimpostare la password.",
        "passwordreset-emailsentusername": "Se c'è un indirizzo di posta elettronica associato con questo nome utente, allora verrà inviata una email per reimpostare la password.",
-       "passwordreset-emailsent-capture": "È stata inviata una email di reimpostazione della password, il contenuto è riportato di seguito.",
-       "passwordreset-emailerror-capture": "È stata generata una email di reimpostazione della password, riportata di seguito. L'invio {{GENDER:$2|all'utente}} non è riuscito: $1",
        "passwordreset-emailsent-capture2": "L'email di reimpostazione della password {{PLURAL:$1|è stata inviata|sono state inviate}}. {{PLURAL:$1|Il nome|L'elenco di nomi}} utente e password è mostrato di seguito.",
        "passwordreset-emailerror-capture2": "Invio di email {{GENDER:$2|all'utente}} non riuscito: $1. {{PLURAL:$3|Il nome|L'elenco di nomi}} utente e password è mostrato di seguito.",
        "passwordreset-nocaller": "Un chiamante deve essere fornito",
        "passwordreset-nodata": "Non è stato fornito né un nome utente né un indirizzo di posta elettronica",
        "changeemail": "Modifica o rimuovi indirizzo di posta elettronica",
        "changeemail-header": "Completa questo modulo per cambiare il tuo indirizzo email. Se vuoi rimuovere l'associazione di qualsiasi indirizzo email dalla tua utenza, lascia il nuovo indirizzo email vuoto quando invii il modulo.",
-       "changeemail-passwordrequired": "Sarà necessario inserire la password per confermare la modifica.",
        "changeemail-no-info": "Devi aver effettuato l'accesso per accedere a questa pagina direttamente.",
        "changeemail-oldemail": "Indirizzo email attuale:",
        "changeemail-newemail": "Nuovo indirizzo email:",
        "showpreview": "Visualizza anteprima",
        "showdiff": "Mostra modifiche",
        "blankarticle": "<strong>Attenzione:</strong> la pagina che stai creando è vuota.\nCliccando nuovamente su \"{{int:savearticle}}\", la pagina sarà creata senza alcun contenuto.",
-       "anoneditwarning": "<strong>Attenzione:</strong> Accesso non effettuato. Se effettuerai delle modifiche il tuo indirizzo IP sarà visibile pubblicamente. Se <strong>[$1 accedi]</strong> o <strong>[$2 crei un'utenza]</strong>, le tue modifiche saranno attribuite al tuo nome utente, insieme ad altri benefici.",
-       "anonpreviewwarning": "''Non è stato eseguito il login. Salvando la pagina, il proprio indirizzo IP sarà registrato nella cronologia.''",
+       "anoneditwarning": "<strong>Attenzione:</strong> non hai effettuato l'accesso. Se effettuerai delle modifiche il tuo indirizzo IP sarà visibile pubblicamente. Se <strong>[$1 accedi]</strong> o <strong>[$2 crei un'utenza]</strong>, le tue modifiche saranno attribuite al tuo nome utente, insieme ad altri benefici.",
+       "anonpreviewwarning": "<em>Non hai effettuato l'accesso. Salvando, il tuo indirizzo IP sarà registrato nella cronologia della pagina.</em>",
        "missingsummary": "<strong>Attenzione:</strong> non è stato specificato l'oggetto di questa modifica. Premendo di nuovo \"{{int:savearticle}}\" la modifica verrà salvata senza.",
        "selfredirect": "<strong>Attenzione:</strong> stai reindirizzando questa pagina a se stessa.\nPotresti aver indicato la destinazione errata per il redirect, o stai modificando la pagina sbagliata.\nSe fai clic nuovamente su \"{{int:savearticle}}\", il redirect sarà creato comunque.",
        "missingcommenttext": "Inserire un commento qui sotto.",
        "undo-nochange": "Sembra che la modifica sia già stata annullata.",
        "undo-summary": "Annullata la modifica $1 di [[Special:Contributions/$2|$2]] ([[User talk:$2|discussione]])",
        "undo-summary-username-hidden": "Annullata la modifica $1 di un utente nascosto",
-       "cantcreateaccounttitle": "Impossibile registrare un utente",
        "cantcreateaccount-text": "La registrazione è stata bloccata da [[User:$3|$3]] per questo indirizzo IP ('''$1''').\n\nLa motivazione del blocco fornita da $3 è la seguente: ''$2''",
        "cantcreateaccount-range-text": "La registrazione da indirizzi IP nell'intervallo <strong>$1</strong>, che include il tuo (<strong>$4</strong>), è stata bloccata da [[User:$3|$3]].\n\nLa motivazione fornita da $3 è <em>$2</em>",
        "viewpagelogs": "Visualizza i registri relativi a questa pagina",
        "watchnologin": "Accesso non effettuato",
        "addwatch": "Aggiungi agli osservati speciali",
        "addedwatchtext": "\"[[:$1]]\" e la sua pagina di discussione sono state aggiunte alla propria [[Special:Watchlist|lista degli osservati speciali]].",
+       "addedwatchtext-talk": "\"[[:$1]]\" e la sua pagina associata sono state aggiunte alla propria [[Special:Watchlist|lista degli osservati speciali]].",
        "addedwatchtext-short": "La pagina \"$1\" è stata aggiunta alla propria lista degli osservati speciali.",
        "removewatch": "Rimuovi dagli osservati speciali",
        "removedwatchtext": "\"[[:$1]]\" e la sua pagina di discussione sono state rimosse dalla propria [[Special:Watchlist|lista degli osservati speciali]].",
+       "removedwatchtext-talk": "\"[[:$1]]\" e la sua pagina associata sono state rimosse dalla propria [[Special:Watchlist|lista degli osservati speciali]].",
        "removedwatchtext-short": "La pagina \"$1\" è stata rimossa dalla propria lista degli osservati speciali.",
        "watch": "Segui",
        "watchthispage": "Segui questa pagina",
        "undeletedrevisions": "{{PLURAL:$1|Una versione recuperata|$1 versioni recuperate}}",
        "undeletedrevisions-files": "{{PLURAL:$1|Una versione|$1 versioni}} e $2 file recuperati",
        "undeletedfiles": "{{PLURAL:$1|Un file recuperato|$1 file recuperati}}",
-       "cannotundelete": "Ripristino non riuscito:\n$1",
+       "cannotundelete": "Alcuni o tutti i ripristini non riusciti:\n$1",
        "undeletedpage": "'''La pagina $1 è stata recuperata'''\n\nConsulta il [[Special:Log/delete|registro delle cancellazioni]] per vedere le cancellazioni e i recuperi più recenti.",
        "undelete-header": "Consulta il [[Special:Log/delete|registro delle cancellazioni]] per vedere le cancellazioni più recenti.",
        "undelete-search-title": "Ricerca nelle pagine cancellate",
        "sp-contributions-newbies-sub": "Per i nuovi utenti",
        "sp-contributions-newbies-title": "Contributi dei nuovi utenti",
        "sp-contributions-blocklog": "blocchi",
-       "sp-contributions-suppresslog": "contributi utente soppressi",
-       "sp-contributions-deleted": "contributi utente cancellati",
+       "sp-contributions-suppresslog": "contributi {{GENDER:$1|utente}} soppressi",
+       "sp-contributions-deleted": "contributi {{GENDER:$1|utente}} cancellati",
        "sp-contributions-uploads": "file caricati",
        "sp-contributions-logs": "registri",
        "sp-contributions-talk": "discussione",
index 6a184d7..321c5d4 100644 (file)
        "passwordreset-emailelement": "利用者名: \n$1\n\n仮パスワード: \n$2",
        "passwordreset-emailsentemail": "このメールアドレスがあなたのアカウントに関連付けられている場合は、パスワードリセットのメールが送信されます。",
        "passwordreset-emailsentusername": "この利用者名に関連付けられたメールアドレスがある場合は、パスワードリセットのメールが送信されます。",
-       "passwordreset-emailsent-capture": "下記の内容の、パスワード再設定メールをお送りしました。",
-       "passwordreset-emailerror-capture": "以下の内容のパスワード再設定メールを生成しましたが、{{GENDER:$2|利用者}}への送信に失敗しました: $1",
        "passwordreset-emailsent-capture2": "パスワードリセットの{{PLURAL:$1|メール}}が送信されました。{{PLURAL:$1|利用者名とパスワード|利用者名とパスワードの一覧}}は以下のとおりです。",
        "passwordreset-emailerror-capture2": "{{GENDER:$2|利用者}}へのメール送信に失敗しました: $1{{PLURAL:$3|利用者名とパスワード|利用者名とパスワードの一覧}}は以下のとおりです。",
        "passwordreset-ignored": "パスワードのリセットが処理されませんでした。プロバイダーが設定されていない可能性があります。",
        "passwordreset-invalideamil": "無効なメールアドレスです",
        "changeemail": "メールアドレスの変更または除去",
        "changeemail-header": "あなたのメールアドレスを変更するには、このフォームを完成させます。もし、あなたのアカウントから任意のメールアドレスの関連付けを削除したい場合は、フォームの送信時に、新しいメールアドレスを空白のままにします。",
-       "changeemail-passwordrequired": "この変更を確認するためにパスワードを入力する必要があります。",
        "changeemail-no-info": "このページに直接アクセスするためにはログインしている必要があります。",
        "changeemail-oldemail": "現在のメールアドレス:",
        "changeemail-newemail": "新しいメールアドレス:",
        "undo-nochange": "指定した編集は既に取り消されたようです。",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|トーク]]) による版 $1 を取り消し",
        "undo-summary-username-hidden": "秘匿された利用者による版 $1 を取り消し",
-       "cantcreateaccounttitle": "アカウントを作成できません",
        "cantcreateaccount-text": "この IP アドレス (<strong>$1</strong>) からのアカウント作成は、[[User:$3|$3]] によってブロックされています。\n\n$3 が示した理由: <em>$2</em>",
        "cantcreateaccount-range-text": "この IP アドレス (<strong>$4</strong>) を含む、IP アドレス範囲 <strong>$1</strong> からのアカウント作成は、[[User:$3|$3]] によってブロックされています。\n\n$3 が示した理由: <em>$2</em>",
        "viewpagelogs": "このページの記録を閲覧",
        "undeletehistorynoadmin": "このページは削除されています。\n削除の理由は、削除前にこのページを編集していた利用者の詳細情報と共に、以下に表示されています。\n管理者以外の利用者には、削除された各版の本文への制限がかけられています。",
        "undelete-revision": "削除されたページ $1 の $4 $5 時点での $3 による版:",
        "undeleterevision-missing": "無効または存在しない版です。\n間違ったリンクをたどったか、この版は既に復元されたか、もしくは保存版から除去された可能性があります。",
+       "undeleterevision-duplicate-revid": "<code>rev_id</code> は既に使用されているため、{{PLURAL:$1|1件の版|$1件の版}}を復元できませんでした。",
        "undelete-nodiff": "これより前の版はありません。",
        "undeletebtn": "復元",
        "undeletelink": "閲覧/復元",
        "undeletedrevisions": "{{PLURAL:$1|$1版}}を復元しました",
        "undeletedrevisions-files": "{{PLURAL:$1|$1版}}と{{PLURAL:$2|$2ファイル}}を復元しました",
        "undeletedfiles": "{{PLURAL:$1|$1ファイル}}を復元しました",
-       "cannotundelete": "復元に失敗しました:\n$1",
+       "cannotundelete": "復元に一部またはすべて失敗しました:\n$1",
        "undeletedpage": "<strong>$1を復元しました。</strong>\n\n最近の削除と復元の記録については[[Special:Log/delete|削除記録]]を参照してください。",
        "undelete-header": "最近削除されたページは[[Special:Log/delete|削除記録]]で確認できます。",
        "undelete-search-title": "削除されたページの検索",
        "sp-contributions-newbies-sub": "新規利用者のみ",
        "sp-contributions-newbies-title": "新規利用者の投稿記録",
        "sp-contributions-blocklog": "ブロック記録",
-       "sp-contributions-suppresslog": "利用者の秘匿された投稿",
-       "sp-contributions-deleted": "削除された投稿の一覧",
+       "sp-contributions-suppresslog": "{{GENDER:$1|利用者}}の秘匿された投稿",
+       "sp-contributions-deleted": "{{GENDER:$1|利用者}}の削除された投稿の一覧",
        "sp-contributions-uploads": "アップロード",
        "sp-contributions-logs": "記録",
        "sp-contributions-talk": "トーク",
index 516949e..2402224 100644 (file)
        "passwordreset-emailtext-user": "Panganggo $1 seka {{SITENAME}} njaluk ganti tembung sandhiné Sampéyan ana ing {{SITENAME}} ($4). {{PLURAL:$3|Rèkèning|Rèkèning-rèkèning}} ngisor iki magepokan karo padunungané layang èlèktronik iki:\n\n$2\n\n{{PLURAL:$3|Tembung sandhi sawetara iki}} bakal kedaluwarsa ing {{PLURAL:$5|sak dina|$5 dina}}.\nSampéyan kudu mlebu log lan milih siji tembung sandhi anyar saiki. Yèn wong liya sing njaluk iki, utawa yèn Sampéyan jebul wis kèlingan tembung sandhiné sing lawas saéngga ora ana niyat kanggo ngganti, Sampéyan bisa ngejaraké wara-wara iki lan bacutaké nganggo tembung sandhiné lawas Sampéyan.",
        "passwordreset-emailelement": "Jeneng panganggo: \n$1\n\nTembung wadi sauntara: \n$2",
        "passwordreset-emailsentemail": "Yèn layang èlèktronik iki nggayut akuning sampéyan, layang kanggo salin tembung wadi bakal dikirim.",
-       "passwordreset-emailsent-capture": "Layang èlèktronik kanggo mbalèkaké tembung sandhi wis dikirim, bisa didelok ngisor iki.",
-       "passwordreset-emailerror-capture": "Layang èlèktronik pangèling tembung sandhi wis digawe, yaiku sing ditampilaké nèng ngisor iki, nanging ora kasil dikirim ing {{GENDER:$2|panganggo}}: $1",
        "changeemail": "Owah utawa busak alamat layang èlèktronik",
        "changeemail-header": "Ganti alamat layang èlèktronik akun",
        "changeemail-no-info": "Sampéyan kudu mlebu log kanggo ngaksès kaca iki langsung.",
        "minoredit": "Iki besutan cilik",
        "watchthis": "Awasi kaca iki",
        "savearticle": "Simpen kaca",
+       "publishpage": "Babar kaca",
+       "publishchanges": "Babar owahan",
        "preview": "Pratuduh",
        "showpreview": "Deleng pratuduh",
        "showdiff": "Tuduhaké owahan",
        "undo-norev": "Besutan iki ora bisa diwurungaké amarga wis ora ana utawa wis dibusak.",
        "undo-summary": "Mbalèkaké owahan $1 déning [[Special:Contributions/$2|$2]] ([[User talk:$2|rembugan]])",
        "undo-summary-username-hidden": "Batalna revisi $1 saking panganggo kang didhelikake",
-       "cantcreateaccounttitle": "Akun ora bisa digawé",
        "cantcreateaccount-text": "Saka alamat IP iki ('''$1''') ora diparengaké nggawé akun utawa rékening. Sing mblokir utawa ora marengaké iku [[User:$3|$3]].\n\nAlesané miturut $3 yaiku ''$2''",
        "cantcreateaccount-range-text": "Nggawe akun saking alamat IP \"$1\", sing termasuk IP sampeyan (<strong>$4</strong>), sampun diblokir kaliyan [[User:$3|$3]].\n\nAlesan pamblokiran yaiku \"$2\"",
        "viewpagelogs": "Deleng cathetaning kaca iki",
        "listfiles_thumb": "Gambar mini",
        "listfiles_date": "Tanggal",
        "listfiles_name": "Jeneng",
-       "listfiles_user": "Panganggo",
+       "listfiles_user": "Naraguna",
        "listfiles_size": "Ukuran (bita)",
        "listfiles_description": "Dèskripsi",
        "listfiles_count": "Vèrsi",
        "filehist-thumb": "Gambar cilik",
        "filehist-thumbtext": "Gambar cilik kanggo owahan $1",
        "filehist-nothumb": "Ora ana miniatur",
-       "filehist-user": "Panganggo",
+       "filehist-user": "Naraguna",
        "filehist-dimensions": "Alang ujur",
        "filehist-filesize": "Gedhené berkas",
        "filehist-comment": "Tanggapan",
        "blocklogpage": "Log pamblokiran",
        "blocklog-showlog": "Panganggo iki wis tau diblokir sakdurungé.\nLog blokiran sumadhiya nèng ngisor kanggo rujukan:",
        "blocklog-showsuppresslog": "Panganggo iki wis tau diblokir lan didhelikaké sakdurungé.\nLog brèdèlan sumadhiya nèng ngisor kanggo rujukan:",
-       "blocklogentry": "mblokir \"[[$1]]\" dipun watesi wekdalipun $2 $3",
-       "reblock-logentry": "Ngowahi sèting pamblokiran [[$1]] kanthi wektu daluwarsa $2 $3",
+       "blocklogentry": "mblokir [[$1]] kanthi wektu kadaluwarsa $2 $3",
+       "reblock-logentry": "ngowah setèlan blokir tumrap [[$1]] kanthi wektu kadaluwarsa $2 $3",
        "blocklogtext": "Ing ngisor iki kapacak log pamblokiran lan panjabelan blokir panganggo.\nAlamat IP sing diblokir sacara otomatis ora ana ing daftar iki.\nMangga mirsani [[Special:BlockList|daftar panganggo sing diblokir]] kanggo daftar blokir pungkasan.",
        "unblocklogentry": "njabel blokir \"$1\"",
        "block-log-flags-anononly": "namung panganggo anonim waé",
        "block-log-flags-hiddenname": "jeneng panganggo didhelikaké",
        "range_block_disabled": "Fungsi pamblokir blok IP kanggo para opsis dipatèni.",
        "ipb_expiry_invalid": "Wektu kadaluwarsa ora absah.",
+       "ipb_expiry_old": "Wektu kadaluwarsa ana ing nguni.",
        "ipb_expiry_temp": "Pamblokiran tumrap jeneng panganggo sing didhelikaké kudu permanèn.",
        "ipb_hide_invalid": "Ora bisa ndhelikaké akun iki; manawa wis kakèhan suntingan.",
        "ipb_already_blocked": "\"$1\" wis diblokir",
        "revdelete-uname-unhid": "jeneng panganggo dituduhaké",
        "revdelete-restricted": "rèstriksi ditrapaké marang para opsis",
        "revdelete-unrestricted": "rèstriksi marang para opsis dijabel",
+       "logentry-block-block": "$1 {{GENDER:$2|mblokir}} {{GENDER:$4|$3}} kanthi wektu kadaluwarsa $5 $6",
+       "logentry-block-reblock": "$1 {{GENDER:$2|ngowah}} setèlan blokir tumrap {{GENDER:$4|$3}} kanthi wektu kadaluwarsa $5 $6",
+       "logentry-suppress-block": "$1 {{GENDER:$2|mblokir}} {{GENDER:$4|$3}} kanthi wektu kadaluwarsa $5 $6",
+       "logentry-suppress-reblock": "$1 {{GENDER:$2|ngowah}} setèlan blokir tumrap {{GENDER:$4|$3}} kanthi wektu kadaluwarsa $5 $6",
        "logentry-move-move": "$1 {{GENDER:$2|ngalih}} kaca $3 nyang $4",
        "logentry-move-move-noredirect": "$1 {{GENDER:$2|mindhahaké}} kaca $3 nèng $4 tanpa ninggalaké pangalihan",
        "logentry-move-move_redir": "$1 {{GENDER:$2|mindhahaké}} kaca $3 nèng $4 nindesi pangalihan liyane",
index d80554d..c634c56 100644 (file)
        "passwordreset-emailtext-user": "$1 есімді қатысушы {{SITENAME}} сайтында ($4) құпия сөзді өзгертуге өтініш білдірді. Мына қатысушы {{PLURAL:$3|аккаунт|аккаунттар}} осы електронды почта қатысты:\n\n$2\n\n{{PLURAL:$3|Бұл уақытша құпия сөз|Бұл уақытша құпия сөздер}} {{PLURAL:$5|бір күнде|$5 күнде}}уақыты аяқталады.\nСіз кіруіңіз және жаңа құпия сөзді таңдауыңыз керек. Егер бұл өтінішті басқа біреу жасаса, немесе сіз  бұрынғы құпия сөзіңізді еске түсірсеңіз, және құпия сөзді ауыстыруды қаламасаңыз, сіз бұл хабарламаны ескермей және бұрыңғы құпия сөзді қолдана беруіңізге болады.",
        "passwordreset-emailelement": "Қатысушы есімі: \n$1\n\nУақытша құпия сөз: \n$2",
        "passwordreset-emailsentemail": "Бұл email мекенжайы тіркелгіңізге байланысқан, сол себепті құпия сөзді өзгерту электронды пошта арқылы жөнелтіледі.",
-       "passwordreset-emailsent-capture": "Құпия сөзді өзгерту электронды пошта арқылы жөнелтілді, ол төменде көрсетілген.",
-       "passwordreset-emailerror-capture": "Құпиясөзді өзгерту электрон хаты жасалды, ол төменде көрсетілген, бірақ ол {{GENDER:$2|қатысушыға}} жөнелтілмеді: $1",
        "changeemail": "Е-пошта мекенжайын өзгерту немесе аластау",
        "changeemail-header": "Е-пошта мекен-жайының өзгертілуі",
        "changeemail-no-info": "Бұл бетке тікелей ену үшін жүйеге кіруіңіз керек.",
        "minoredit": "Бұл шағын өңдеме",
        "watchthis": "Бұл бетті бақылау",
        "savearticle": "Бетті сақтау",
+       "savechanges": "Өзгерістерді сақтау",
+       "publishpage": "Бетті жариялау",
+       "publishchanges": "Өзгерістерді жариялау",
        "preview": "Қарап шығу",
        "showpreview": "Алдын-ала қарау",
        "showdiff": "Өзгерістерді көрсет",
        "undo-nochange": "Өңдеме әлдеқашан жоққа шығарылғаны анықталды.",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|т]]) істеген нөмір $1 нұсқасын жоққа шығарды",
        "undo-summary-username-hidden": "$1 нұсқасын жасырылған қатысушы жоққа шығарды",
-       "cantcreateaccounttitle": "Тіркелгі жасалмады",
        "cantcreateaccount-text": "Бұл IP мекенжайдан (<strong>$1</strong>) жаңа тіркелгі жасауын [[User:$3|$3]] бұғаттаған.\n\n$3 есімді қатысушының келтіріген себебі: <em>$2</em>",
        "cantcreateaccount-range-text": "<strong>$1</strong> ауқымындағы IP мекенжайдан сіздің IP мекенжайыңыз да кіреді (<strong>$4</strong>) жаңа тіркелгі жасауын [[User:$3|$3]] бұғаттаған.\n\n$3 есімді қатысушының келтіріген себебі: ''$2'",
        "viewpagelogs": "Бұл беттің журнал оқиғаларын қарау",
        "tooltip-ca-nstab-category": "Санат бетін қарау",
        "tooltip-minoredit": "Бұны шағын өңдеме деп белгілеу",
        "tooltip-save": "Жасаған өзгерістеріңізді сақтау",
+       "tooltip-publish": "Өзгерістеріңізді жариялаңыз",
        "tooltip-preview": "Сақтаудың алдынан жасаған өзгерістеріңізді қарап шығыңыз!",
        "tooltip-diff": "Мәтінге қандай өзгерістерді жасағаныңызды қарау.",
        "tooltip-compareselectedversions": "Беттің екі бөлектенген нұсқасы айырмасын қарау.",
        "mw-widgets-dateinput-placeholder-day": "ЖЖЖЖ-АА-КК",
        "mw-widgets-dateinput-placeholder-month": "ЖЖЖЖ-АА",
        "mw-widgets-titleinput-description-new-page": "бет жоқ екен",
-       "mw-widgets-titleinput-description-redirect": "$1 дегенге бағыттату",
-       "api-error-blacklisted": "Өтініш, сипаттама атауының басқасын таңдаңыз."
+       "mw-widgets-titleinput-description-redirect": "$1 дегенге бағыттату"
 }
index 61e1a21..5d2c25c 100644 (file)
@@ -36,7 +36,7 @@
        "tog-hideminor": "ಇತ್ತೀಚಿನ ಬದಲಾವಣೆಗಳಲ್ಲಿ ಚಿಕ್ಕಪುಟ್ಟ ಸಂಪಾದನೆಗಳನ್ನು ಅಡಗಿಸಿ",
        "tog-hidepatrolled": "ಪಹರೆಯಲ್ಲಿ ಆದ ಸಂಪಾದನೆಗಳನ್ನು ಇತ್ತೀಚೆಗಿನ ಬದಲಾವಣೆಗಳಲ್ಲಿ ಅಡಗಿಸು",
        "tog-newpageshidepatrolled": "ಪಹರೆಯಲ್ಲಿ ಆದ ಪುಟಗಳನ್ನು ಹೊಸ ಪುಟಗಳ ಪಟ್ಟಿಯಲ್ಲಿ ಅಡಗಿಸು",
-       "tog-extendwatchlist": "à²\95à³\87ವಲ à²\87ತà³\8dತà³\80à²\9aà³\86à²\97ಿನ à²¬à²¦à²²à²¾à²µà²£à³\86à²\97ಳಲà³\8dಲದà³\86, à²¸à²\82ಬà²\82ಧಿತ à²\8eಲà³\8dಲಾ à²¬à²¦à²²à²¾à²µà²£à³\86à²\97ಳನà³\8dನà³\81 à²¤à³\8bರà³\81ವà²\82ತà³\86 à²ªà²\9fà³\8dà²\9fಿಯನà³\8dನà³\81 à²µà²¿à²¸à³\8dತರಿಸಿ",
+       "tog-extendwatchlist": "ಕೇವಲ ಇತ್ತೀಚೆಗಿನ ಬದಲಾವಣೆಗಳಲ್ಲದೆ, ಎಲ್ಲಾ ಬದಲಾವಣೆಗಳನ್ನು ತೋರುವಂತೆ ಪಟ್ಟಿಯನ್ನು ವಿಸ್ತರಿಸಿ",
        "tog-usenewrc": "ಹೆಚ್ಚು ವರ್ಧಿಸಲಾದ ಇತ್ತೀಚಿನ ಬದಲಾವಣೆಗಳು ಪುಟ ಬಳಸು",
        "tog-numberheadings": "ತಲೆಬರಹಗಳಿಗೆ ಅಂಕಿಗಳನ್ನು ತೋರಿಸು",
        "tog-showtoolbar": "ಸಂಪಾದನೆಯ ಉಪಕರಣಗಳ ಪಟ್ಟಿಯನ್ನು ತೋರು",
        "faqpage": "Project:ಸಾಮಾನ್ಯವಾಗಿ ಕೇಳಲಾಗುವ ಪ್ರಶ್ನೆಗಳು",
        "actions": "ಕ್ರಿಯೆಗಳು",
        "namespaces": "ನಾಮವರ್ಗಗಳು",
-       "variants": "ಹಲವà³\81",
+       "variants": "ವà³\8dಯತà³\8dಯಾಸ à²¹à³\8aà²\82ದಿರà³\81ವ",
        "navigation-heading": "ಸಂಚರಣೆ ಪಟ್ಟಿ",
        "errorpagetitle": "ದೋಷ",
        "returnto": "$1 ಗೆ ಹಿಂತಿರುಗಿ.",
        "undelete_short": "{{PLURAL:$1|ಒಂದು ಸಂಪಾದನೆಯ|$1 ಸಂಪಾದನೆಗಳ}} ಅಳಿಸುವಿಕೆಯನ್ನು ತೊಡೆದುಹಾಕು",
        "viewdeleted_short": "ನೋಟ {{PLURAL:$1|೧ ಅಳಿಸಲ್ಪಟ್ಟ ಸಂಪಾದನೆ|$1 ಅಳಿಸಲ್ಪಟ್ಟ ಸಂಪಾದನೆಗಳು}}",
        "protect": "ಸಂರಕ್ಷಿಸು",
-       "protect_change": "ಬದಲಾಯಿಸಿ",
+       "protect_change": "ಬದಲಾಯಿಸà³\81",
        "protectthispage": "ಈ ಪುಟವನ್ನು ಸಂರಕ್ಷಿಸಿ",
-       "unprotect": "ರà²\95à³\8dಷಣà³\86ಯನà³\8dನà³\81 à²¬à²¦à²²à²¾à²µà²£à³\86",
-       "unprotectthispage": "à²\88 à²ªà³\81à²\9fದ à²°à²\95à³\8dಷಣà³\86ಯನà³\8dನà³\81 à²¬à²¦à²²à²¾à²¯à²¿à²¸à²²à³\81",
+       "unprotect": "ರà²\95à³\8dಷಣà³\86ಯನà³\8dನà³\81 à²¬à²¦à²²à²¾à²¯à²¿à²¸à³\81",
+       "unprotectthispage": "ಈ ಪುಟದ ರಕ್ಷಣೆಯನ್ನು ಬದಲಾಯಿಸು",
        "newpage": "ಹೊಸ ಪುಟ",
-       "talkpage": "à²\88 à²ªà³\81à²\9fದ à²¬à²\97à³\8dà²\97à³\86 à²\9aರà³\8dà²\9aà³\86 à²®à²¾à²¡ಿ",
+       "talkpage": "à²\88 à²ªà³\81à²\9fವನà³\8dನà³\81 à²\9aರà³\8dà²\9aಿಸಿ",
        "talkpagelinktext": "ಚರ್ಚೆ",
        "specialpage": "ವಿಶೇಷ ಪುಟ",
        "personaltools": "ವೈಯಕ್ತಿಕ ಉಪಕರಣಗಳು",
        "talk": "ಚರ್ಚೆ",
        "views": "ನೋಟಗಳು",
        "toolbox": "ಉಪಕರಣಗಳು",
-       "userpage": "ಸದಸ್ಯರ ಪುಟ ತೋರು",
+       "userpage": "ಸದಸ್ಯರ ಪುಟವನ್ನು ವೀಕ್ಷಿಸು",
        "projectpage": "ಯೋಜನೆಯ ಪುಟವನ್ನು ನೋಡು",
        "imagepage": "ಕಡತದ ಪುಟ ವೀಕ್ಷಿಸಿ",
        "mediawikipage": "ಸಂದೇಶ ಪುಟವನ್ನು ನೋಡು",
        "templatepage": "ಟೆಂಪ್ಲೇಟು ಪುಟವನ್ನು ವೀಕ್ಷಿಸಿ",
        "viewhelppage": "ಸಹಾಯ ಪುಟ ತೋರು",
-       "categorypage": "ವರ್ಗ ಪುಟ ತೋರು",
+       "categorypage": "ವರ್ಗದ ಪುಟವನ್ನು ವೀಕ್ಷಿಸಿ",
        "viewtalkpage": "ಚರ್ಚೆಯನ್ನು ವೀಕ್ಷಿಸಿ",
        "otherlanguages": "ಇತರ ಭಾಷೆಗಳಲ್ಲಿ",
        "redirectedfrom": "($1 ಇಂದ ಪುನರ್ನಿರ್ದೇಶಿತ)",
        "jumpto": "ಇಲ್ಲಿಗೆ ಹೋಗು:",
        "jumptonavigation": "ಸಂಚರಣೆ",
        "jumptosearch": "ಹುಡುಕು",
-       "view-pool-error": "$1",
+       "view-pool-error": "ಕ್ಷಮಿಸಿ, ಸದ್ಯಕ್ಕೆ ಸರ್ವರ್‌ಗಳ ಮೇಲೆ ಹೆಚ್ಚಿನ ಹೊರೆ ಇದೆ.\nಬಹಳಷ್ಟು ಬಳಕೆದಾರರು ಈ ಸಂಪನ್ಮೂಲವನ್ನು ನೋಡಲು ಪ್ರಯತ್ನಿಸುತ್ತಿದ್ದಾರೆ.\nನೀವು ಈ ಸಂಪನ್ಮೂಲವನ್ನು ಇನ್ನೊಮ್ಮೆ ನೋಡಲು ಪ್ರಯತ್ನಿಸುವ ಮೊದಲು ಸ್ವಲ್ಪಹೊತ್ತು ಕಾಯಿರಿ.\n\n$1",
        "generic-pool-error": "ಕ್ಷಮಿಸಿ, ಸದ್ಯಕ್ಕೆ ಸರ್ವರ್‌ಗಳ ಮೇಲೆ ಹೆಚ್ಚಿನ ಹೊರೆ ಇದೆ.\nಬಹಳಷ್ಟು ಬಳಕೆದಾರರು ಈ ಸಂಪನ್ಮೂಲವನ್ನು ನೋಡಲು ಪ್ರಯತ್ನಿಸುತ್ತಿದ್ದಾರೆ.\nನೀವು ಈ ಸಂಪನ್ಮೂಲವನ್ನು ಇನ್ನೊಮ್ಮೆ ನೋಡಲು ಪ್ರಯತ್ನಿಸುವ ಮೊದಲು ಸ್ವಲ್ಪಹೊತ್ತು ಕಾಯಿರಿ.",
        "pool-timeout": "ಕಾಲಾವಕಾಶ ಲಾಕ್ ಕಾಯುವುದು",
        "pool-queuefull": "ಪ್ರಕ್ರಿಯೆಯನ್ನು ವಿಶೇಷ ಕ್ಯು ಪೂರ್ಣ",
        "passwordreset-domain": "ಕ್ಷೇತ್ರ:",
        "passwordreset-email": "ಇ-ಮೇಲ್ ವಿಳಾಸ:",
        "passwordreset-emailsentemail": "ಪ್ರವೇಶಪದವನ್ನು ಪುನಃಸ್ಥಾಪಿಸಿದ ಮಿಂಚಂಚೆಯನ್ನು ಕಳುಹಿಸಲಾಗಿದೆ.",
-       "passwordreset-emailsent-capture": "ಪ್ರವೇಶಪದವನ್ನು ಪುನಃಸ್ಥಾಪಿಸಿದ ಮಿಂಚಂಚೆಯನ್ನು ಕಳುಹಿಸಲಾಗಿದೆ,ಇದನ್ನು ಈ ಕೆಳಗೆ ತೋರಿಸಲಾಗಿದೆ.",
        "changeemail": "ಮಿಂಚಂಚೆ ವಿಳಾಸವನ್ನು ಬದಲಾಯಿಸಿ",
        "changeemail-no-info": "ನೀವು ಈ ಪುಟವನ್ನು ನೇರತಲುಪಲು ಲಾಗಿನ್ ಆಗಿರುವುದು ಆವಶ್ಯಕ.",
        "changeemail-oldemail": "ಪ್ರಸ್ತುತ ಮಿಂಚಂಚೆ ವಿಳಾಸ:",
        "minoredit": "ಇದು ಚುಟುಕಾದ ಬದಲಾವಣೆ",
        "watchthis": "ಈ ಪುಟವನ್ನು ವೀಕ್ಷಿಸಿ",
        "savearticle": "ಪುಟವನ್ನು ಉಳಿಸಿ",
+       "publishpage": "ಪುಟವನ್ನು ಪ್ರಕಟಿಸು",
+       "publishchanges": "ಬದಲಾವಣೆಗಳನ್ನು ಪ್ರಕಟಿಸು",
        "preview": "ಮುನ್ನೋಟ",
        "showpreview": "ಮುನ್ನೋಟ ತೋರಿಸು",
        "showdiff": "ಬದಲಾವಣೆಗಳನ್ನು ತೋರಿಸು",
        "undo-success": "ಸಂಪಾದನೆಯನ್ನು ವಜಾ ಮಾಡಬಹುದು. ದಯವಿಟ್ಟು ಕೆಳಗಿರುವ ತುಲನೆಯನ್ನು ಪರೀಕ್ಷಿಸಿ ನೀವು ಮಾಡಲು ಇಚ್ಚಿಸಿರುವುದನ್ನು ಖಾತ್ರಿ ಮಾಡಿಕೊಂಡು ವಜಾಗೊಳಿಸುವ ಕ್ರಿಯೆಯನ್ನು \nಪೂರ್ಣಗೊಳಿಸಲು ಬದಲಾವಣೆಗಳನ್ನು ಉಳಿಸಿ.",
        "undo-norev": "ಸಂಪಾದನೆಯನ್ನು ವಜಾಗೊಳಿಸಲು ಸಾದ್ಯವಿಲ್ಲ ಏಕೆಂದರೆ ಒಂದೊ ಇದು ಅಸ್ತಿತ್ವದಲ್ಲಿ ಇಲ್ಲ ಅಧವಾ ಇದು ಅಳಿಸಲ್ಪಟ್ಟಿದೆ",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|talk]]) ರ $1 ಪರಿಷ್ಕರಣೆಯನ್ನು ವಜಾ ಮಾಡಿ",
-       "cantcreateaccounttitle": "ಖಾತೆಯನ್ನು ಸೃಷ್ಟಿಸಲಾಗುತ್ತಿಲ್ಲ",
        "viewpagelogs": "ಈ ಪುಟಗಳ ದಾಖಲೆಗಳನ್ನು ವೀಕ್ಷಿಸಿ",
        "nohistory": "ಈ ಪುಟಕ್ಕೆ ಬದಲಾವಣೆಗಳ ಇತಿಹಾಸ ಇಲ್ಲ.",
        "currentrev": "ಈಗಿನ ತಿದ್ದುಪಡಿ",
index f548224..5b666c7 100644 (file)
        "userlogin-resetlink": "로그인 정보를 잊으셨나요?",
        "userlogin-resetpassword-link": "비밀번호를 잊으셨나요?",
        "userlogin-helplink2": "로그인에 대한 도움말",
-       "userlogin-loggedin": "이미 {{GENDER:$1|$1}} 사용자로 로그인되어 있습니다.\n다른 사용자로 로그인하려면 아래의 양식을 사용하세요.",
+       "userlogin-loggedin": "이미 {{GENDER:$1|$1}}님으로 로그인되어 있습니다.\n다른 사용자로 로그인하려면 아래의 양식을 사용하세요.",
        "userlogin-reauth": "당신이 {{GENDER:$1|$1}}임을 검증하려면 다시 로그인해야 합니다.",
        "userlogin-createanother": "다른 계정 만들기",
        "createacct-emailrequired": "이메일 주소",
        "createacct-loginerror": "계정 만들기는 성공했으나 자동으로 로그인하지 못했습니다. [[Special:UserLogin|수동으로 로그인]]해 주십시오.",
        "noname": "사용자 계정 이름이 올바르지 않습니다.",
        "loginsuccesstitle": "로그인함",
-       "loginsuccess": "<strong>{{SITENAME}}에 \"$1\" 계정으로 로그인했습니다.</strong>",
+       "loginsuccess": "<strong>{{SITENAME}}에 \"$1\"으로 로그인했습니다.</strong>",
        "nosuchuser": "이름이 \"$1\"인 사용자는 없습니다.\n사용자 이름은 대소문자를 구별합니다.\n철자가 맞는지 확인해주세요. [[Special:CreateAccount|새 계정을 만들 수도 있습니다]].",
        "nosuchusershort": "이름이 \"$1\"인 사용자는 없습니다.\n철자가 맞는지 확인하세요.",
        "nouserspecified": "사용자 계정 이름을 입력하지 않았습니다.",
        "passwordreset-emailelement": "사용자 이름: \n$1\n\n임시 비밀번호: \n$2",
        "passwordreset-emailsentemail": "당신의 계정과 연결된 이메일 주소가 있다면, 비밀번호 재설정 메일이 전해질 것입니다.",
        "passwordreset-emailsentusername": "이 사용자 이름과 연결된 이메일 주소가 있다면 비밀번호 초기화 이메일이 전송됩니다.",
-       "passwordreset-emailsent-capture": "비밀번호 재설정 이메일이 발송되었으며, 아래에 나타나 있습니다.",
-       "passwordreset-emailerror-capture": "비밀번호 재설정 이메일이 생성되어 아래에 나타나 있지만, {{GENDER:$2|사용자}}에게 발송하는 데에는 실패했습니다: $1",
        "passwordreset-emailsent-capture2": "비밀번호 재설정 이메일을 보냈습니다. {{PLURAL:$1|사용자 이름과 비밀번호는|사용자 이름과 비밀번호의 목록은}} 아래에 나타납니다.",
        "passwordreset-emailerror-capture2": "{{GENDER:$2|사용자}} 이메일 보내기 실패: $1 {{PLURAL:$3|사용자 이름과 비밀번호가|사용자 이름과 비밀번호의 목록이}} 아래에 나타납니다.",
        "passwordreset-nocaller": "호출자를 지정해야 합니다",
        "passwordreset-nodata": "사용자 이름이나 이메일 주소가 지정되지 않았습니다",
        "changeemail": "이메일 주소를 바꾸거나 제거하기",
        "changeemail-header": "이메일 주소를 바꾸려면 이 양식을 채우세요. 계정에서 이메일 연동을 취소하고 싶다면 양식을 제출할 때 새 이메일 주소를 공란으로 두세요.",
-       "changeemail-passwordrequired": "변경을 적용하려면 비밀번호를 입력해야 합니다.",
        "changeemail-no-info": "이 페이지에 직접 접근하려면 로그인해야 합니다.",
        "changeemail-oldemail": "현재 이메일 주소:",
        "changeemail-newemail": "새 이메일 주소:",
        "undo-nochange": "편집이 이미 되돌려진 것으로 나타납니다.",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|토론]])의 $1판 편집을 되돌림",
        "undo-summary-username-hidden": "숨겨진 사용자가 $1 판을 되돌림",
-       "cantcreateaccounttitle": "계정을 만들 수 없습니다",
        "cantcreateaccount-text": "현재 IP 주소('''$1''')는 [[User:$3|$3]] 사용자에 의해 계정 만들기가 차단되었습니다.\n\n차단 이유는 다음과 같습니다: $2",
        "cantcreateaccount-range-text": "당신의 IP 주소(<strong>$4</strong>)가 속해 있는 <strong>$1</strong> 대역에서의 계정 만들기를 [[User:$3|$3]]님이 차단했습니다.\n\n$3님이 제시한 이유는 \"$2\"입니다.",
        "viewpagelogs": "이 문서의 기록 보기",
        "prefs-advancedrendering": "고급 설정",
        "prefs-advancedsearchoptions": "고급 설정",
        "prefs-advancedwatchlist": "고급 설정",
-       "prefs-displayrc": "보이기 설정",
-       "prefs-displaywatchlist": "보이기 설정",
+       "prefs-displayrc": "표시 설정",
+       "prefs-displaywatchlist": "표시 설정",
        "prefs-tokenwatchlist": "토큰",
        "prefs-diffs": "차이",
        "prefs-help-prefershttps": "이 사용자 환경 설정은 다음 로그인부터 적용됩니다.",
        "uploadstash-errclear": "파일을 지우는 데 실패했습니다.",
        "uploadstash-refresh": "파일 목록을 새로 고침",
        "uploadstash-thumbnail": "섬네일 보기",
+       "uploadstash-exception": "비공개로 업로드할 수 없습니다 ($1): \"$2\".",
        "invalid-chunk-offset": "청크 오프셋이 잘못되었습니다.",
        "img-auth-accessdenied": "접근이 거부됨",
        "img-auth-nopathinfo": "PATH_INFO를 잃었습니다.\n서버가 이 정보를 받을 수 있도록 설정되어 있지 않습니다.\n이러한 경우는 서버가 CGI 기반이고 img_auth를 지원하지 않을 때 나타날 수 있습니다.\nhttps://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization을 참조하십시오.",
        "protectedpages-performer": "보호한 사용자",
        "protectedpages-params": "보호 변수",
        "protectedpages-reason": "이유",
-       "protectedpages-submit": "문서 보이기",
+       "protectedpages-submit": "문서 표시",
        "protectedpages-unknown-timestamp": "알 수 없음",
        "protectedpages-unknown-performer": "알 수 없는 사용자",
        "protectedtitles": "만들기 보호된 표제어 목록",
        "protectedtitles-summary": "이 페이지는 현재 만들기 보호가 설정되어 있는 문서 제목을 나열합니다. 보호된 기존 문서들의 목록을 보려면 [[{{#special:ProtectedPages}}|{{int:protectedpages}}]]을 보세요.",
        "protectedtitlesempty": "해당 조건에 맞는 만들기 금지 표제어가 없습니다.",
-       "protectedtitles-submit": "제목 보이기",
+       "protectedtitles-submit": "제목 표시",
        "listusers": "사용자 목록",
        "listusers-editsonly": "기여가 있는 사용자만 보기",
        "listusers-creationsort": "계정을 만든 날짜순으로 정렬",
        "emailccsubject": "$1에게 보낸 메시지의 복사본: $2",
        "emailsent": "이메일 보냄",
        "emailsenttext": "이메일을 보냈습니다.",
-       "emailuserfooter": "이 이메일은 {{SITENAME}}의 $1님이 $2 사용자에게 \"{{int:emailuser}}\" 기능을 통해 보냈습니다.",
+       "emailuserfooter": "이 이메일은 {{SITENAME}}의 $1님이 $2에게 \"{{int:emailuser}}\" 기능을 통해 보냈습니다.",
        "usermessage-summary": "시스템 메시지 남기기",
        "usermessage-editor": "시스템 메신저",
        "usermessage-template": "MediaWiki:UserMessage",
        "undeletehistorynoadmin": "이 문서는 삭제되었습니다.\n삭제된 이유와 삭제되기 전에 이 문서를 편집한 사용자가 아래에 나와 있습니다.\n삭제된 문서의 내용을 보려면 관리자 권한이 필요합니다.",
        "undelete-revision": "삭제된 $1 문서의 $4 $5 버전 (기여자 $3):",
        "undeleterevision-missing": "해당 판이 잘못되었거나 존재하지 않습니다.\n잘못된 링크를 따라왔거나, 특정 판이 이미 되살렸거나 데이터베이스에서 제거되었을 수도 있습니다.",
+       "undeleterevision-duplicate-revid": "{{PLURAL:$1|해당 판의|해당 판들의}} <code>rev_id</code>가 이미 사용 중이기 때문에 {{PLURAL:$1|한 개의 판|$1개의 판}}을 복구할 수 없습니다.",
        "undelete-nodiff": "이전의 판이 없습니다.",
        "undeletebtn": "되살리기",
        "undeletelink": "보기/되살리기",
        "undeletedrevisions": "{{PLURAL:$1|판 1개|판 $1개}}를 되살렸습니다",
        "undeletedrevisions-files": "{{PLURAL:$1|판 1개|판 $1개}}와 {{PLURAL:$2|파일 1개|파일 $2개}}를 되살렸습니다",
        "undeletedfiles": "{{PLURAL:$1|파일 1개|파일 $1개}}를 되살렸습니다",
-       "cannotundelete": "되살리는 데 실패했습니다:\n$1",
+       "cannotundelete": "일부 또는 모든 항목의 되살리기를 실패했습니다:\n$1",
        "undeletedpage": "<strong>$1 문서를 되살렸습니다.</strong>\n\n[[Special:Log/delete|삭제 기록]]에서 최근의 삭제 및 되살리기 기록을 볼 수 있습니다.",
        "undelete-header": "최근에 삭제한 문서에 대한 기록은 [[Special:Log/delete|여기]]에서 볼 수 있습니다.",
        "undelete-search-title": "삭제된 문서 검색",
        "sp-contributions-newbies-sub": "새 사용자의 기여",
        "sp-contributions-newbies-title": "새 사용자의 기여",
        "sp-contributions-blocklog": "차단 기록",
-       "sp-contributions-suppresslog": "숨겨진 사용자 기여",
-       "sp-contributions-deleted": "삭제된 사용자 기여",
+       "sp-contributions-suppresslog": "숨겨진 {{GENDER:$1|사용자}} 기여",
+       "sp-contributions-deleted": "삭제된 {{GENDER:$1|사용자}} 기여",
        "sp-contributions-uploads": "올린 파일",
        "sp-contributions-logs": "기록",
        "sp-contributions-talk": "토론",
        "pageinfo-header-edits": "편집 역사",
        "pageinfo-header-restrictions": "문서 보호",
        "pageinfo-header-properties": "문서 속성",
-       "pageinfo-display-title": "보여줄 제목",
+       "pageinfo-display-title": "표시 제목",
        "pageinfo-default-sort": "기본 정렬 키",
        "pageinfo-length": "문서 길이 (바이트)",
        "pageinfo-article-id": "문서 ID",
index af6b90c..6afca3d 100644 (file)
        "difference-title": "Ero šivun ”$1” versijien välillä",
        "lineno": "Rivi $1:",
        "editundo": "lakauttua",
-       "diff-multi-sameuser": "({{PLURAL:$1|Yksi keškitasšon versija |$1 keškitašon versijua}} šamalta käyttäjältä ei näytetty)",
+       "diff-multi-sameuser": "({{PLURAL:$1|Yksi keškitašon versija |$1 keškitašon versijua}} šamalta käyttäjältä ei näytetty)",
        "searchresults": "Eččimisen tulokšet",
        "searchresults-title": "Eči \"$1\"",
        "prevn": "iellini {{PLURAL:$1|$1}}",
index 139dabe..3586530 100644 (file)
        "passwordreset-emailelement": "Metmaacher Name: \n$1\n\nEijmohl-Paßwoot: \n$2",
        "passwordreset-emailsentemail": "Wann dat en <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i>-Adräß vun Der es, dann weed en <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i> för Dinge Zohjang verschek, öm e neu Paßwoot ze krijje.",
        "passwordreset-emailsentusername": "Wann heh dä Metmaacher en <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i>-Adräß hät, dann weed en <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i> verschek, öm e neu Paßwoot ze krijje.",
-       "passwordreset-emailsent-capture": "En <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i> met Aanjahbe zom neue Paßwoot för der Zohjang heh es verschek woode. Heh dronger kanns De se lässe.",
-       "passwordreset-emailerror-capture": "En <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i> met Aanjahbe zom neue Paßwoot för der Zohjang heh sullt verschek wääde, ävver dat Verscheke aan {{GENDER:$2|dä|dat|dä Metmaacher|de|dat}} $2 hät nit jeflup: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|En <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i> es|De <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i>s sin|Nix es}} verschek woode, öm e neu Paßwoot ze krijje. {{PLURAL:$1|Dä Nahme vum Metmaacher un dat Paßwood|Di Leß met dä Nahme un Paßwööter|Nix weed}} heh noh aanjezeijsch.",
        "passwordreset-emailerror-capture2": "{{GENDER:$2|Däm|Däm|Däm Metmaacher|Dä|Däm}} $1 en <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i> ze scheke hät nit jeflupp: {{PLURAL:$3|Dä Nahme vum Metmaacher un dat Paßwood|Di Leß met dä Nahme un Paßwööter|Nix weed}} heh noh aanjezeijsch.",
        "passwordreset-nocaller": "Entärne Fähler: Ene Oprohfer moß aanjejovve sin.",
        "passwordreset-nodata": "Keine Metmaacher_Nahme un kein Adräß för de <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i> es aanjejovve woode.",
        "changeemail": "Donn en Adräß för de <i lang=\"en\">e-mail</i> ändere udder fott schmiiße",
        "changeemail-header": "Donn heh dat Fommulaa ußfölle, öm Ding Adräß för de <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"„de eläktrohnesche Poß“\">e-mail</i> ze ändere. Wann De en Adräß loß wähde wells, maach dat Fäld läddesch, ih dat De dat Fommolaa loß scheks.",
-       "changeemail-passwordrequired": "Do moß Ding Paßwood enjävve, öm di Änderong ze beschtähteje.",
        "changeemail-no-info": "Do mööts ald enjelogg sin, öm tiräk op di Sigg jonn ze dörve",
        "changeemail-oldemail": "Ding Address för de <i lang=\"en\">e-mail</i> es jäz:",
        "changeemail-newemail": "Ding neue Address för de <i lang=\"en\">e-mail</i> sull wääde:",
        "undo-nochange": "Di Änderong schingk ald retuur jemaat woode ze sin.",
        "undo-summary": "Di Änderong $1 wood {{GENDER:$2|vum|vum|vumm Metmaacher|vun dä|vum}} [[Special:Contributions/$2|$2]] ([[User talk:$2|Klaaf]]) zeröck jenomme.",
        "undo-summary-username-hidden": "Nemm di Väsjohn $1 vun enem verschtoche Metmaacher widder retuhr.",
-       "cantcreateaccounttitle": "Kann keine Zojang enrichte",
        "cantcreateaccount-text": "Dä [[User:$3|$3]] hät verbodde, dat mer sich vun dä IP-Adress '''$1''' uß als ene neue Metmaacher aanmelde könne soll.\n\nAls Jrund för et Sperre es enjedraare: ''$2''",
        "cantcreateaccount-range-text": "Ne neue Metmaacher aanmälde vun <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"Internet Protocol\">IP</i>-Adräße em Berett vun <strong>$1</strong>, woh de Dinge dren es, wood vum {{GENDER:$3|vum|vum|vumm Metmaacher|vun dä|vum}} [[User:$3|$3]] verbodde.\nDer Jrond: <em><$2</em>\n\nDing <i lang=\"en\" xml:lang=\"en\" dir=\"ltr\" title=\"Internet Protocol\">IP</i>-Adräß es: <strong>$4</strong>",
        "viewpagelogs": "De Logböcher för heh di Sigg beloore",
index b8ab58d..d2d6046 100644 (file)
        "minoredit": "Haec est recensio minor",
        "watchthis": "Hanc paginam observare",
        "savearticle": "Hanc redactionem servare",
+       "publishpage": "Hanc paginam divulgare",
+       "publishchanges": "Hanc recensionem divulgare",
        "preview": "Praevidere",
        "showpreview": "Prospectum ostendere",
        "showdiff": "Mutationes ostendere",
        "parser-template-loop-warning": "Ansa formulae detecta: [[$1]]",
        "undo-norev": "Recensio abrogari non potuit quia non est aut deleta est.",
        "undo-summary": "Abrogans recensionem $1 ab usore [[Special:Contributions/$2|$2]] ([[User talk:$2|Disputatio]])",
-       "cantcreateaccounttitle": "Non licuit nomen tibi imponere",
        "cantcreateaccount-text": "Ex hoc loco IP ('''$1''') nomen sibi imponere ab usore [[User:$3|$3]] interdicitur.\nQui hanc causam dedit: ''$2''",
        "viewpagelogs": "Vide acta huius paginae",
        "nohistory": "Huic paginae non est historia.",
        "shared-repo-from": "apud {{grammar:accusative|$1}}",
        "shared-repo": "repositorium commune",
        "shared-repo-name-wikimediacommons": "Vicimedia Communia",
+       "upload-disallowed-here": "Hunc facisculum substituere tibi non licet.",
        "filerevert": "Revertere $1",
        "filerevert-legend": "Reverti fasciculum",
        "filerevert-intro": "Reversurus es '''[[Media:$1|$1]]''' ad [$4 redactionem quae $2, $3 facta erat].",
        "tooltip-t-recentchangeslinked": "Nuper mutata in paginis quibus haec pagina nectit",
        "tooltip-feed-rss": "Fluxus RSS huius paginae",
        "tooltip-feed-atom": "Atom feed",
-       "tooltip-t-contributions": "Videre conlationes huius usoris",
+       "tooltip-t-contributions": "Videre conlationes huius usoris ($1)",
        "tooltip-t-emailuser": "Mittere litteras electronicas huic usori",
        "tooltip-t-upload": "Fasciculos imponere",
        "tooltip-t-specialpages": "Index paginarum specialium",
        "tooltip-ca-nstab-category": "Videre paginam categoriae",
        "tooltip-minoredit": "Indicare hanc recensionem minorem",
        "tooltip-save": "Servare mutationes tuas",
+       "tooltip-publish": "Hanc recensionem divulgare",
        "tooltip-preview": "Sinet prospicere, quod mutationes tuas effecerint. Utere, quaesumus, hac facultate, antequam servas!",
        "tooltip-diff": "Comparabit hanc redactionem cum superiore earumque differentias notabit",
        "tooltip-compareselectedversions": "Inspicere, quatenus contenta redactionum selectarum inter se distent",
index 8fd5a9a..ad0b104 100644 (file)
@@ -53,6 +53,7 @@
        "tog-watchlisthidebots": "Ännerunge vu Botten op menger Iwwerwaachungslëscht verstoppen",
        "tog-watchlisthideminor": "Kleng Ännerungen op menger Iwwerwaachungslëscht verstoppen",
        "tog-watchlisthideliu": "Ännerunge vun ugemellte Benotzer verstoppen",
+       "tog-watchlistreloadautomatically": "D'Iwwerwaachungslëscht nei lueden esoubal wéi e Filter geännert ass (JavaScript gëtt gebraucht)",
        "tog-watchlisthideanons": "Ännerunge vun anonyme Benotzer (IP-Adressen) verstoppen",
        "tog-watchlisthidepatrolled": "Iwwerkuckten Ännerungen op der Iwwerwaachungslëscht verstoppen",
        "tog-watchlisthidecategorization": "Kategorisatioun vu Säite verstoppen",
        "createaccountreason": "Grond:",
        "createacct-reason": "Grond",
        "createacct-reason-ph": "Fir wat Dir een anere Benotzerkonnt uleet",
+       "createacct-reason-help": "Message deen am Logbuch vun den ugeluechte Benotzerkonte gewise gëtt",
        "createacct-submit": "Äre Benotzerkont uleeën",
        "createacct-another-submit": "Benotzerkont uleeën",
        "createacct-continue-submit": "Virufuere mam Uleeë vum Benotzerkont",
        "nocookiesnew": "De Benotzerkont gouf ugeluecht, awer Dir sidd net ageloggt.\n{{SITENAME}} brauch fir dës Funktioun Cookien.\nDir hutt d'Cookien desaktivéiert.\nAktivéiert déi w.e.g. a loggt Iech da mat Ärem neie Benotzernomm a mat dem respektive Passwuert an.",
        "nocookieslogin": "{{SITENAME}} benotzt Cookië beim Umelle vun de Benotzer.\nDir hutt Cookien ausgeschalt.\nAktivéiert d'Cookien w.e.g. a versicht et nach eng Kéier.",
        "nocookiesfornew": "De Benotzerkont gouf net ugeluecht, well mir seng Quell net bestëmme konnten.\nVergewëssert Iech datt Dir Cookien zouloosst, luet dës Säit nei a probéiert nach emol.",
+       "createacct-loginerror": "De Benotzerkont gouf ugeluecht, mä Dir konnt net automatesch ageloggt ginn. [[Special:UserLogin|Loggt Iech w.e.g. manuell an]].",
        "noname": "Dir hutt kee gëltege Benotzernumm uginn.",
        "loginsuccesstitle": "Ageloggt",
        "loginsuccess": "'''Dir sidd elo als \"$1\" op {{SITENAME}} ugemellt.'''",
        "botpasswords-label-cancel": "Ofbriechen",
        "botpasswords-label-delete": "Läschen",
        "botpasswords-label-resetpassword": "D'Passwuert zrécksetzen",
+       "botpasswords-help-grants": "All Berechtegung gëtt Zougang op déi Benotzerrechter déi e Benotzerkont schonn huet. Kuckt d'[[Special:ListGrants|Tabell vun de Berechtigunge]] fir méi Informatiounen.",
+       "botpasswords-label-restrictions": "Limite fir d'Benotzen:",
        "botpasswords-label-grants-column": "Accordéiert",
        "botpasswords-bad-appid": "Den Numm vum Bot \"$1\" ass net valabel.",
+       "botpasswords-insert-failed": "De Botnumm \"$1\" konnt net dobäigesat ginn. Gouf e schonn derbäigesat?",
+       "botpasswords-created-title": "Botpasswuert ugeluecht",
        "botpasswords-created-body": "D'Botpasswuert fir de Bot-Numm \"$1\" vum Benotzer ''$2'' gouf ugeluecht.",
        "botpasswords-updated-title": "Botpasswuert aktualiséiert",
        "botpasswords-updated-body": "D'Botpasswuert fir de Bot-Numm \"$1\" vum Benotzer ''$2'' gouf aktualiséiert.",
        "botpasswords-deleted-title": "Botpasswuert geläscht",
        "botpasswords-deleted-body": "D'Botpasswuert fir de Bot-Numm \"$1\" vum Benotzer ''$2'' gouf geläscht.",
+       "botpasswords-newpassword": "Dat neit Passwuert fir sech mat <strong>$1</strong> anzeloggen ass <strong>$2</strong>.\n<em>Versuergt dat fir sech spéider dorop ze referéieren.</em>",
        "botpasswords-not-exist": "De Benotzer \"$1\" huet kee Botpasswuert mam Numm \"$2\".",
        "resetpass_forbidden": "Passwierder kënnen net geännert ginn.",
        "resetpass_forbidden-reason": "Passwierder kënnen net geännert ginn: $1",
        "passwordreset-emailelement": "Benotzernumm: \n$1\n\nTemporärt Passwuert: \n$2",
        "passwordreset-emailsentemail": "Wann dës E-Mailadress mat Ärem Benotzerkont assoziéiert ass, da gëtt Eng E-Mail fir d'Passwuert zréckzesetze geschéckt.",
        "passwordreset-emailsentusername": "Wann eng E-Mailadress mat dësem Benotzernumm associéiert ass, da gëtt Eng E-Mail fir d'Passwuert zeréckzesetze geschéckt.",
-       "passwordreset-emailsent-capture": "Eng Mail fir d'Passwuert zréckzesetze gouf geschéckt, Dir gesitt se hei drënner.",
-       "passwordreset-emailerror-capture": "Eng Mail fir d'Passwuert zréckzesetze gouf geschéckt, Dir gesitt se hei drënner, awer de {{GENDER:$2|Benotzer}} konnt se net kréien: $1",
        "passwordreset-invalideamil": "Net-valabel E-Mail-Adress",
        "passwordreset-nodata": "Et gouf weder e Benotzernumm nach e Passwuert uginn",
        "changeemail": "E-Mail-Adress änneren oder ewechhuelen",
        "changeemail-header": "Fëllt dëse Formulaire aus fir Är E-Mailadress z'änneren.  Wann Dir d'Verbindung tëscht Ärer E-Mailadress an Ärem Benotzerkont ewechhuele wëllt, da loosst d'Feld e-Mailadress eidel wann Dir de Formulaire späichert.",
-       "changeemail-passwordrequired": "Dir musst Äert Passwuert agi fir dës Ännerung ze konfirméieren.",
        "changeemail-no-info": "Dir musst ageloggt sinn, fir direkt op dës Säit ze kommen.",
        "changeemail-oldemail": "Aktuell Mailadress:",
        "changeemail-newemail": "Nei Mailadress:",
        "undo-nochange": "D'Ännerung gouf anscheinend schonn zeréckgesat.",
        "undo-summary": "Ännerung $1 vu(n) [[Special:Contributions/$2|$2]] ([[User talk:$2|Diskussioun]] | [[Special:Contributions/$2|{{MediaWiki:Contribslink}}]]) annulléieren.",
        "undo-summary-username-hidden": "Versioun $1 vun engem verstoppte Benotzer zrécksetzen",
-       "cantcreateaccounttitle": "Benotzerkont konnt net opgemaach ginn",
        "cantcreateaccount-text": "D'Opmaache vu Benotzerkonten vun dëser IP Adress ('''$1''') gouf vum [[User:$3|$3]] gespaart.\n\nDe Benotzer $3 huet \"$2\" als Grond uginn.",
        "cantcreateaccount-range-text": "D'Uleeë vu Benotzerkonte vun IP-Adressen aus dem Beräich \"$1\", zu deem Är IP-Adress (<strong>$4</strong>) gehéiert, gouf vum [[User:$3|$3]] gespaart.\n\nDe Grond den den $3 uginn huet ass <em>$2</em>",
        "viewpagelogs": "Logbicher fir dës Säit weisen",
        "mergehistory-fail-bad-timestamp": "Zäitstempel ass net valabel.",
        "mergehistory-fail-invalid-source": "Quellsäit ass net valabel.",
        "mergehistory-fail-invalid-dest": "Zilsäit ass net valabel.",
+       "mergehistory-fail-permission": "Net genuch Rechter fir den Historique vun de Versiounen ze fusionéieren.",
+       "mergehistory-fail-self-merge": "Quell an Zilsäit sinn déi selwecht.",
        "mergehistory-fail-toobig": "D'zesummeleeë vun der Lëscht vun de Versioune konnt net gemaach ginn well méi wéi d'Limite vun $1 {{PLURAL:$1|Versioun|Versioune}} geréckelt géife ginn",
        "mergehistory-no-source": "Originalsäit \"$1\" gëtt et net.",
        "mergehistory-no-destination": "Zilsäit \"$1\" gëtt et net.",
        "right-createpage": "Säiten uleeën (déi keng Diskussiounssäite sinn)",
        "right-createtalk": "Diskussiounssäiten uleeën",
        "right-createaccount": "Nei Benotzerkonten uleeën",
+       "right-autocreateaccount": "Automatesch alogge mat engem externe Benotzerkont",
        "right-minoredit": "Ännerungen als kleng markéieren",
        "right-move": "Säite réckelen",
        "right-move-subpages": "Säiten zesumme mat hiren Ënnersäite réckelen",
        "grant-editmywatchlist": "Ännert Är Iwwerwaachungslëscht",
        "grant-editpage": "Säiten déi et gëtt änneren",
        "grant-editprotected": "Gespaart Säiten änneren",
+       "grant-highvolume": "Massenännerungen",
        "grant-oversight": "Benotzer verstoppen a Versioune läschen",
        "grant-patrol": "Ännerungen op Säiten kontrolléieren",
        "grant-protect": "Säite spären an entspären",
        "action-createpage": "dës Säit uleeën",
        "action-createtalk": "dës Diskussiounssäit uleeën",
        "action-createaccount": "dëse Benotzerkont unzeleeën",
+       "action-autocreateaccount": "automatesch dësen externe Benotzerkont opzemaachen",
        "action-history": "d'Versioune vun dëser Säit weisen",
        "action-minoredit": "dës Ännerung als kleng Ännerung ze markéieren",
        "action-move": "dës Säit ze réckelen",
        "upload-dialog-button-upload": "Eroplueden",
        "upload-form-label-infoform-title": "Detailer",
        "upload-form-label-infoform-name": "Numm",
+       "upload-form-label-infoform-name-tooltip": "E kuerzen an uniquen Titel fir de Fichier, deen och als Numm vum Fichier benotzt gëtt. Dir kënnt derbäi Text mat Espace benotzen. D'Erweiderung vum Fichier soll net ugi ginn.",
        "upload-form-label-infoform-description": "Beschreiwung",
+       "upload-form-label-infoform-description-tooltip": "Beschreift w.e.g. kuerz dat Wichtegst vun dësem Wierk.\nFir eng Photo, ernimmt déi Haaptsaachen déi drop sinn, d'Geleeënheet oder d'Plaz.",
        "upload-form-label-usage-title": "Benotzung",
        "upload-form-label-usage-filename": "Numm vum Fichier",
        "upload-form-label-own-work": "Dëst ass mäin eegent Wierk",
        "upload-form-label-infoform-categories": "Kategorien",
        "upload-form-label-infoform-date": "Datum",
+       "upload-form-label-not-own-work-local-generic-local": "Dir kënnt och [[Special:Upload|d'Standardsäit vum Eroplueden]] ausprobéieren.",
        "backend-fail-stream": "De Fichier $1 konnt net iwwerdroe ginn.",
        "backend-fail-backup": "De Fichier $1 konnt net geséchert ginn.",
        "backend-fail-notexists": "De Fichier $1 gëtt et net.",
        "apisandbox-deprecated-parameters": "Vereelst Parameter",
        "apisandbox-submit-invalid-fields-title": "E puer Felder sinn net valabel.",
        "apisandbox-results": "Resultater",
+       "apisandbox-sending-request": "Schécke vun der API-Ufro...",
+       "apisandbox-loading-results": "Ofruffe vun den API-Resultater...",
        "apisandbox-request-url-label": "URL fir Ufroen:",
        "apisandbox-request-time": "Dauer vun der Ufro: {{PLURAL:$1|$1 ms}}",
        "apisandbox-alert-page": "Felder op dëser Säit sinn net valabel.",
        "trackingcategories": "Tracking-Kategorien",
        "trackingcategories-msg": "Tracking-Kategorie",
        "trackingcategories-name": "Numm vum Message",
+       "restricted-displaytitle-ignored": "Säite mat ignoréierten Säitentitele fir unzeweisen",
        "noindex-category-desc": "D'Säit gëtt net vu Botten indexéiert, well dat magescht Wuert <code><nowiki>__NOINDEX__</nowiki></code> dran ass a well se an engem Nummraum ass, an deem déi Markéierung erlaabt ass.",
        "index-category-desc": "D'Säit huet <code><nowiki>__INDEX__</nowiki></code> an ass an engem Nummraum, wou déi Markéierung erlaabt ass an dofir gëtt d'Säit vu Sichroboter indexéiert wou dat normalerweis net de Fall wier.",
        "post-expand-template-inclusion-category-desc": "D'Säit ass méi grouss wéi <code>$wgMaxArticleSize</code> nom expandéiere vun alle Schablounen, dofir goufen e puer Schablounen net expandéiert.",
        "rollbacklinkcount": "{{PLURAL:$1|Eng Ännerung|$1 Ännerungen}} zrécksetzen",
        "rollbacklinkcount-morethan": "méi wéi {{PLURAL:$1|Eng Ännerung|$1 Ännerungen}} zrécksetzen",
        "rollbackfailed": "Zrécksetzen huet net geklappt",
+       "rollback-missingparam": "An der Ufro feelen obligatoresch Parameteren.",
        "cantrollback": "Lescht Ännerung kann net zréckgesat ginn. De leschten Auteur ass deen eenzegen Auteur vun dëser Säit.",
        "alreadyrolled": "Déi lescht Ännerung vun der Säit [[:$1]] vum [[User:$2|$2]] ([[User talk:$2|talk]]{{int:pipe-separator}}[[Special:Contributions/$2|{{int:contribslink}}]]); kann net zréckgesat ginn;\neen Aneren huet dat entweder scho gemaach oder nei Ännerungen agedroen.\n\nDéi lescht Ännerung vun der Säit war vum [[User:$3|$3]] ([[User talk:$3|Diskussioun]]{{int:pipe-separator}}[[Special:Contributions/$3|{{int:contribslink}}]]).",
        "editcomment": "De Resumé vun der Ännerung war: <em>$1</em>.",
        "revertpage": "Ännerunge vum [[Special:Contributions/$2|$2]] ([[User talk:$2|Diskussioun]]) zréckgesat op déi lescht Versioun vum [[User:$1|$1]]",
        "revertpage-nouser": "Zréckgesaten Ännerungen duerch e verstoppte Benotzer op déi lescht Versioun vum {{GENDER:$1|[[User:$1|$1]]}}",
        "rollback-success": "D'Ännerunge vum $1 goufen zréckgesat op déi lescht Versioun vum $2.",
+       "rollback-success-notify": "Zréckgesat Ännerunge vum $1:\nzréckgeännert op déi lescht Versioun vum $2. [$3 Ännerunge weisen]",
        "sessionfailure-title": "Setzungsfeeler",
        "sessionfailure": "Et schéngt e Problem mat Ärer Loginseance ze ginn;\nDës Aktioun gouf aus Sécherheetsgrënn ofgebrach, fir ze verhënneren datt Är Seance piratéiert ka ginn.\nKlickt w.e.g. op \"Zréck\" a luet déi Säit vun där Dir komm sidd nei, a versicht et dann nach eng Kéier.",
        "changecontentmodel": "De Modell vum Inhalt vun enger Säit änneren",
        "changecontentmodel-submit": "Änneren",
        "changecontentmodel-success-title": "De Modell vum Inhalt gouf geännert",
        "changecontentmodel-success-text": "Den Typ vum Inhalt vu(n) [[:$1]] gouf geännert.",
+       "changecontentmodel-cannot-convert": "Den Inhalt vu(n) [[:$1]] kann net op den Typ $2 ëmgewandelt ginn.",
+       "changecontentmodel-emptymodels-title": "Keng Modeller fir Inhalter disponibel",
        "logentry-contentmodel-change-revertlink": "zrécksetzen",
        "logentry-contentmodel-change-revert": "zrécksetzen",
        "protectlogpage": "Protektiounslogbuch",
        "undeletedrevisions": "$1 {{PLURAL:$1|Versioun gouf|$1 Versioune goufe}} restauréiert",
        "undeletedrevisions-files": "{{PLURAL:$1|1 Versioun|$1 Versiounen}} a(n) {{PLURAL:$2|1 Fichier|$2 Fichiere}} goufe restauréiert",
        "undeletedfiles": "$1 {{PLURAL:$1|Fichier gouf|Fichiere goufe}} restauréiert",
-       "cannotundelete": "D'Restauratioun huet net funktionéiert:\n$1",
+       "cannotundelete": "E puer oder all d'Restauratiounen hunn net funktionéiert:\n$1",
        "undeletedpage": "'''$1''' gouf restauréiert.\n\nAm [[Special:Log/delete|Läsch-Logbuch]] fannt Dir déi geläscht a restauréiert Säiten.",
        "undelete-header": "Kuckt [[Special:Log/delete|Läschlescht]] fir rezent geläscht Säiten.",
        "undelete-search-title": "Geläscht Säite sichen",
        "namespace": "Nummraum:",
        "invert": "Auswiel ëmdréinen",
        "tooltip-invert": "Klickt dës Këscht fir Ännerungen am erausgesichten Nummraum (an den associéierten Nummraim wa se markéiert sinn) ze verstoppen.",
+       "tooltip-whatlinkshere-invert": "Markéiert dës Këscht fir Linke vu Säiten am erausgesichten Nummraum ze verstoppen.",
        "namespace_association": "Associéierten Nummraum",
        "tooltip-namespace_association": "Dës Këscht uklicke fir den Diskussiouns oder den associéierten Nummraum mat dem erausgesichten Nummraum matanzebezéien",
        "blanknamespace": "(Haapt)",
        "sp-contributions-newbies-sub": "Fir déi Nei",
        "sp-contributions-newbies-title": "Kontributioune vun neie Benotzer",
        "sp-contributions-blocklog": "Spärlescht",
-       "sp-contributions-suppresslog": "geläscht Benotzerkontributiounen",
-       "sp-contributions-deleted": "geläscht Kontributiounen",
+       "sp-contributions-suppresslog": "geläscht {{GENDER:$1|Benotzerkontributiounen}}",
+       "sp-contributions-deleted": "geläscht {{GENDER:$1|Benotzerkontributiounen}}",
        "sp-contributions-uploads": "Eropgeluede Fichieren",
        "sp-contributions-logs": "Logbicher",
        "sp-contributions-talk": "diskutéieren",
        "confirmemail_body_set": "Iergendeen, wahrscheinlech Dir selwer, vun der IP-Adress $1,\nhuet d'E-Mail-Adress vum Benotzerkont \"$2\" op dës Adress op {{SITENAME}} geännert.\n\nFir ze confirméieren datt dëse Benotzerkont Iech wierklech gehéiert a fir d'E-Mailfonctiounen op {{SITENAME}} ze reaktivéieren, maacht dës Link an Ärem Browser op:\n\n$3\n\nWann de Benotzerkont Iech *net* gehéiert, da klickt op dëse Link fir d'Confirmatioun vun der E-Mail-Adress auszeschalten:\n\n$5\n\nDëse Confirmatiounscode leeft den $4 of.",
        "confirmemail_invalidated": "Confirmatioun vun der E-Mail-Adress annulléiert",
        "invalidateemail": "Annulléier d'E-Mailconfirmation",
+       "notificationemail_subject_changed": "D'E-Mail-Adress déi op {{SITENAME}} enregistréiert war gouf geännert",
        "notificationemail_subject_removed": "D'E-Mail-Adress déi op {{SITENAME}} enregistréiert war gouf ewechgeholl",
        "scarytranscludedisabled": "[Interwiki-Abannung ass ausgeschalt]",
        "scarytranscludefailed": "[D'Siche no der Schabloun fir $1 huet net funktionéiert]",
        "tags-edit-existing-tags-none": "<em>Keng</em>",
        "tags-edit-new-tags": "Nei Markéierungen (tags):",
        "tags-edit-add": "Dës Markéierungen (tags) dobäisetzen:",
+       "tags-edit-remove": "Dës Markéierungen (tags) ewechhuelen:",
        "tags-edit-remove-all-tags": "(all Markéierungen ewechhuelen)",
        "tags-edit-chosen-no-results": "Keng Markéierunge fonnt déi passen",
        "tags-edit-reason": "Grond:",
        "htmlform-cloner-delete": "Ewechhuelen",
        "htmlform-cloner-required": "Mindestens ee Wäert ass obligatoresch.",
        "htmlform-title-badnamespace": "[[:$1]] ass net am Nummraum \"{{ns:$2}}\".",
+       "htmlform-title-not-creatable": "\"$1\" ass kee Säitentitel deen ugeluecht ka ginn",
        "htmlform-title-not-exists": "$1 gëtt et net.",
        "htmlform-user-not-exists": "<strong>$1</strong> gëtt et net.",
        "htmlform-user-not-valid": "<strong>$1</strong> ass kee valabele Benotzernumm.",
        "mw-widgets-titleinput-description-new-page": "Säit gëtt et nach net",
        "mw-widgets-titleinput-description-redirect": "viruleeden op $1",
        "sessionprovider-generic": "$1-Sessiounen",
+       "sessionprovider-mediawiki-session-cookiesessionprovider": "cookie-baséiert Sessiounen",
+       "sessionprovider-nocookies": "Cookië sinn eventuell desaktivéiert. Vergewëssert Iech datt Dir d'Cookien aktivéiert hutt a probéiert nach eng Kéier.",
        "randomrootpage": "Zoufalls-Stammsäit",
        "log-action-filter-block": "Typ vun der Spär:",
+       "log-action-filter-delete": "Läschtyp:",
+       "log-action-filter-import": "Importtyp:",
+       "log-action-filter-move": "Réckeltyp:",
        "log-action-filter-protect": "Typ vu Spär",
+       "log-action-filter-upload": "Eropluedtyp:",
        "log-action-filter-all": "All",
        "log-action-filter-block-block": "Spären",
        "log-action-filter-block-reblock": "Ännere vun enger Spär",
        "log-action-filter-block-unblock": "Spär ophiewen",
        "log-action-filter-delete-delete": "Säite läschen",
+       "log-action-filter-delete-revision": "Läsche vun enger Versioun",
        "log-action-filter-import-interwiki": "Transwiki-Import",
+       "log-action-filter-import-upload": "Import duerch Eropluede vun engem XML",
        "log-action-filter-move-move_redir": "Réckele mat Iwwerschreiwe vu Viruleedungen",
+       "log-action-filter-newusers-create": "Ugeluecht vun engem anonyme Benotzer",
+       "log-action-filter-newusers-create2": "Ugeluecht vun engem registréierte Benotzer",
+       "log-action-filter-newusers-autocreate": "Automatesch ugeluecht",
        "log-action-filter-patrol-patrol": "Manuell Kontroll",
        "log-action-filter-patrol-autopatrol": "Automatesch Kontroll",
        "log-action-filter-protect-protect": "Spär",
        "log-action-filter-rights-autopromote": "Automatesch Ännerung",
        "log-action-filter-upload-upload": "Neien Upload",
        "log-action-filter-upload-overwrite": "Nees eroplueden",
+       "authmanager-create-disabled": "D'Opmaache vu Benotzerkonten ass gespaart.",
+       "authmanager-create-from-login": "Fir Äre Benotzerkont unzeleeën fëllt w.e.g. d'Felder hei drënner aus.",
        "authmanager-authplugin-setpass-failed-title": "Änner vum Passwuert huet net funktionéiert",
+       "authmanager-authplugin-setpass-bad-domain": "Net valabelen Domain.",
        "authmanager-userdoesnotexist": "De Benotzerkont \"$1\" ass net registréiert.",
        "authmanager-retype-help": "Passwuert nach eng Kéier fir ze konfirméieren",
        "authmanager-email-label": "E-Mail",
        "authmanager-provider-temporarypassword": "Temporäert Passwuert:",
        "authprovider-resetpass-skip-label": "Iwwersprangen",
        "authprovider-resetpass-skip-help": "D'Zrécksetze vum Passwuert iwwersprangen",
+       "authform-notoken": "Toke feelt",
+       "authform-wrongtoken": "Falschen Token",
        "specialpage-securitylevel-not-allowed-title": "Net erlaabt",
        "specialpage-securitylevel-not-allowed": "Leider däerft Dir dës Säit net benotze well Är Identitéit net konnt iwwerpréift ginn.",
        "cannotauth-not-allowed-title": "Erlaabnes refuséiert",
index 5c22e14..779c36c 100644 (file)
        "tog-hidepatrolled": "Gemarkeerde wieziginge verberge in recente wieziginge",
        "tog-newpageshidepatrolled": "Gemarkeerde pagina's verberge in de lies mit nuuj pagina's",
        "tog-extendwatchlist": "Oetgebreide volglies gebroeke óm alle verangeringe te zeen en neet allein de lèste",
-       "tog-usenewrc": "Tuun verangeringe per pagina in recènte verangeringe en volglies (Javascript nudig)",
+       "tog-usenewrc": "Tuun verangeringe per pagina in recènte verangeringe en volglies",
        "tog-numberheadings": "Köpkes automatisch nummere",
-       "tog-showtoolbar": "Laot edit toolbar zeen",
-       "tog-editondblclick": "Bewirk pagina's bie 'ne dobbelklik (JavaScript)",
-       "tog-editsectiononrightclick": "Secties bewirke mit 'ne rechtermoesklik op sectietitels (JavaScript nudig)",
+       "tog-showtoolbar": "Laot bewirkingwerkbalk zeen",
+       "tog-editondblclick": "Bewirk pagina's bie 'ne dobbelklik",
+       "tog-editsectiononrightclick": "Secties bewirke mit 'ne rechtermoesklik op sectietitels",
        "tog-watchcreations": "Volg autematis pagina's die ich aanmaak en bestenj die ich upload",
        "tog-watchdefault": "Voog pagina's em bestenj die se bewirks toe aan dien volglies",
        "tog-watchmoves": "Volg autematis pagina's en bestenj die ich verplaats",
        "tog-watchdeletion": "Volg autematis pagina's en bestenj die ich ewegsjaf",
+       "tog-watchuploads": "Nuuj besjtenj die ich upload toevoge aan mienn volglies",
+       "tog-watchrollback": "Pagina's boe-in ich get höb óngedaon gemaak autematis volge",
        "tog-minordefault": "Markeer sjtanderd alle bewirkinge es klein",
        "tog-previewontop": "Veurvertuin baove bewèrkingsveld tuine",
        "tog-previewonfirst": "Preview laote zien bie de ierste bewirking",
        "tog-shownumberswatching": "'t Aantal gebroekers tuine die dees pagina volg",
        "tog-oldsig": "Bestaonde ongerteikening:",
        "tog-fancysig": "Es wikiteks behanjele (zonder autematische verwiezing)",
-       "tog-uselivepreview": "\"live veurbesjouwing\" gebroeke (vereis JavaScript - experimenteel)",
+       "tog-uselivepreview": "\"live veurbesjouwing\" gebroeke",
        "tog-forceeditsummary": "'n Melding gaeve bie 'n laeg samevatting",
        "tog-watchlisthideown": "Eige bewirkinge verberge op mien volglies",
        "tog-watchlisthidebots": "Botbewirkinge op mien volglies verberge",
        "tog-watchlisthideminor": "Klein bewirkinge op mien volglies verberge",
        "tog-watchlisthideliu": "Bewirkinge van aangemelde gebroekers op mien volglies versjtaeke",
+       "tog-watchlistreloadautomatically": "Herlaaj de volglies autematis es 'n filter is verangerd (JavaScript vereis)",
        "tog-watchlisthideanons": "Bewirkinge van anonieme gebroekers op mien volglies versjtaeke",
        "tog-watchlisthidepatrolled": "Gemarkeerde wieziginge op mien volglies verberge",
+       "tog-watchlisthidecategorization": "Verberg categorisatie  van  pagina's",
        "tog-ccmeonemails": "'n Kopie nao mich versjikke van de e-mail dae ich nao anger gebroekers sjik",
        "tog-diffonly": "Pagina-inhaud zónger verangeringe neet tuine",
        "tog-showhiddencats": "Verbórge categorië tuine",
        "tog-norollbackdiff": "Wieziginge eweglaote nao trökdrieje",
-       "tog-useeditwarning": "Waorssjoew mich es ich 'n bewerkdje pagina die nag neet is opgeslage wil verlaote",
+       "tog-useeditwarning": "Waarsjoew mich es ich 'n bewerkde pagina die nog neet is opgeslage wil verlaote",
+       "tog-prefershttps": "Ummer 'n beveiligde verbinding gebroeke es ich ingelog bin",
        "underline-always": "Altied",
        "underline-never": "Noets",
        "underline-default": "Sjtanderd van de browser",
        "oct": "okt",
        "nov": "nov",
        "dec": "dec",
+       "january-date": "$1 jannewarie",
+       "february-date": "$1 fibberwarie",
+       "march-date": "$1 miert",
+       "april-date": "$1 april",
+       "may-date": "$1 mei",
+       "june-date": "$1 juni",
+       "july-date": "$1 juli",
+       "august-date": "$1 augustus",
+       "september-date": "$1 september",
+       "october-date": "$1 oktober",
+       "november-date": "$1 november",
+       "december-date": "$1 december",
+       "period-am": "AM",
+       "period-pm": "PM",
        "pagecategories": "{{PLURAL:$1|Categorie|Categorieë}}",
        "category_header": "Artikele in categorie \"$1\"",
        "subcategories": "Subcategorieë",
        "newwindow": "(in nuuj venster)",
        "cancel": "Aafbraeke",
        "moredotdotdot": "Miè...",
+       "morenotlisted": "Deze lies is neet compleet.",
        "mypage": "Mien gebroekerspagina",
        "mytalk": "Euverlèk",
        "anontalk": "Euverlèk veur dit IP adres",
        "actions": "Hanjeling",
        "namespaces": "Naamruumdes",
        "variants": "Anger vorme",
+       "navigation-heading": "Navigatiemenu",
        "errorpagetitle": "Fout",
        "returnto": "Truuk nao $1.",
        "tagline": "Van {{SITENAME}}",
        "permalink": "Permanente link",
        "print": "Aafdrukke",
        "view": "Bekieke",
-       "edit": "Bewèrk",
+       "view-foreign": "Betrach op $1",
+       "edit": "Bewirk",
+       "edit-local": "Lokaal besjrieving bewirke",
        "create": "Aanmake",
-       "editthispage": "Pagina bewirke",
+       "create-local": "Lokaal besjrieving toeveuge",
+       "editthispage": "Dees pagina bewirke",
        "create-this-page": "Dees pagina aanmake",
        "delete": "Wisse",
        "deletethispage": "Wisse",
+       "undeletethispage": "Dees pagina trökzètte",
        "undelete_short": "$1 {{PLURAL:$1|bewirking|bewirkinge}} trökzètte",
        "viewdeleted_short": "{{PLURAL:$1|ein eweggesjafde versie|$1 eweggesjafde versies}} bekieke",
        "protect": "Besjirm",
        "otherlanguages": "Anger tale",
        "redirectedfrom": "(Doorverweze van $1)",
        "redirectpagesub": "Doorverwiespagina",
+       "redirectto": "Doorverwieze nao:",
        "lastmodifiedat": "Dees pagina is 't lèts verangerd op $2, $1.",
        "viewcount": "Dees pagina is {{PLURAL:$1|1 kier|$1 kier}} bekeke.",
        "protectedpage": "Beveiligde pagina",
        "pool-errorunknown": "Ónbekènde fout",
        "aboutsite": "Euver {{SITENAME}}",
        "aboutpage": "Project:Info",
-       "copyright": "De inhawd is besjikbaar ónger de $1.",
+       "copyright": "De inhawd is besjikbaar ónger de $1 behauve is angers aangegeve.",
        "copyrightpage": "{{ns:project}}:Auteursrechte",
        "currentevents": "In 't nuujs",
        "currentevents-url": "Project:In 't nuujs",
        "disclaimers": "Aafwiezinge aansjprakelikheid",
        "disclaimerpage": "Project:Algemein aafwiezing aansjprakelikheid",
        "edithelp": "Hulp bie bewirke",
+       "helppage-top-gethelp": "Hölp",
        "mainpage": "Veurblaad",
        "mainpage-description": "Veurblaad",
        "policy-url": "Project:Beleid",
        "hidetoc": "versjtaek",
        "collapsible-collapse": "Inklappe",
        "collapsible-expand": "Oetklappe",
+       "confirmable-confirm": "Bis {{GENDER:$1|diech}} zeker?",
+       "confirmable-yes": "Jao",
+       "confirmable-no": "Nein",
        "thisisdeleted": "$1 tuine of trökzètte?",
        "viewdeleted": "$1 tuine?",
        "restorelink": "{{PLURAL:$1|ein eweggesjafde versie|$1 eweggesjafde versies}}",
        "nstab-template": "Sjabloon",
        "nstab-help": "Hulppagina",
        "nstab-category": "Categorie",
+       "mainpage-nstab": "Veurblaad",
        "nosuchaction": "Gevraogde hanjeling besjteit neet",
        "nosuchactiontext": "De opdrach in de URL is ongeldig.\nMäögelik höbs te 'n typefout gemaak in de URL, of 'n verkierde verwiezing gevolg.\n't Kan ouch wieze op 'n fout in de software van {{SITENAME}}.",
        "nosuchspecialpage": "D'r besjteit gein speciaal pagina mit deze naam",
        "passwordreset-emailtext-user": "Gebroeker $1 op de site {{SITENAME}} haet dien gebroekersgegaeves veur {{SITENAME}} ($4) ópgevraog.\nDe volgende {{PLURAL:$3|gebroeker is|gebroekers zint}} gekoppeld aan dit e-mailadres:\n\n$2\n\n{{PLURAL:$3|Dit tiedelik wachwaord vervilt|Dees tiedelike wachweurd vervallen}} euver {{PLURAL:$5|einen daag|$5 daag}}.\nMel dich aan en veranger 't wachwaord noe. Es se dit verzeuk neet zelf hes gedaon, of es se 't oorspronkelik wachwaord nog kins en 't neet anges wils, laot dit berich den en blief dien aad wachwaord gebroeke.",
        "passwordreset-emailelement": "Gebroekersnaam: \n$1\n\nTiedelik wachwaord: \n$2",
        "passwordreset-emailsentemail": "d'r Is per mail 'n herinnering versjik.",
-       "passwordreset-emailsent-capture": "d'r Is 'ne herinneringse-mail versjik. Deze weurt hieónger getuind.",
-       "passwordreset-emailerror-capture": "d'r Is 'ne herinneringse-mail aangemaak. Deze weurt hieónger getuind. 't Verzènje nao de gebroeker is mislök óm de volgende raeje: $1",
        "changeemail": "Veranger dien e-mailadres",
        "changeemail-header": "Veranger 't e-mailadres van miene gebroekersnaam",
        "changeemail-no-info": "Doe moos aangemeld zien ierdets doe dees pagina gebroeke kens.",
        "minoredit": "Dit is 'n klein verangering",
        "watchthis": "Volg dees pagina",
        "savearticle": "Pagina opsjlaon",
+       "publishpage": "Pagina publicere",
+       "publishchanges": "Verangeringe publicere",
        "preview": "Naokieke",
        "showpreview": "Betrach dees bewirking",
        "showdiff": "Toen verangeringe",
        "token_suffix_mismatch": "'''Dien bewerking is geweigerd omdat dien client de laesteikes in 't bewerkingstoken onjuist haet behandeld. De bewerking is geweigerd om verminking van de paginateks te veurkomme. Dit gebeurt soms es d'r een webgebaseerde proxydienst wurt gebroek die foute bevat.'''",
        "edit_form_incomplete": "'''Sommige ongerdeile van 't bewerkingsformuleer höbbe de server neet bereik. Controleer of dien bewerkinge intak zien en perbeer 't obbenuits.'''",
        "editing": "Bewirkingspagina: $1",
-       "creating": "$1 aanmakendj",
+       "creating": "Aanmake van $1",
        "editingsection": "Bewirke van sectie van $1",
        "editingcomment": "Bewirke $1 (commentair)",
        "editconflict": "Bewirkingsconflik: $1",
        "undo-failure": "De verangering kòs neet ongedaon gemaak waere waeges angere striedige verangeringe.",
        "undo-norev": "De bewerking kon neet ongedaan gemaak waere, omdat die neet besteet of is verwijderd.",
        "undo-summary": "Versie $1 van [[Special:Contributions/$2|$2]] ([[User talk:$2|euverlèk]]) óngedaon gemaak.",
-       "cantcreateaccounttitle": "Aanmake gebroeker misluk.",
        "cantcreateaccount-text": "'t Aanmake van gebroekers van dit IP-adres ('''$1''') is geblokkeerd door [[User:$3|$3]].\n\nDe door $3 opgegaeve reje is ''$2''",
        "viewpagelogs": "Logbeuk veur dees pagina tuine",
        "nohistory": "Dees pagina is nog neet bewirk.",
        "special-characters-group-lao": "Lao",
        "special-characters-group-khmer": "Cambodzjaans",
        "mw-widgets-dateinput-placeholder-day": "JJJJ-MM-DD",
-       "mw-widgets-dateinput-placeholder-month": "JJJJ-MM",
-       "api-error-blacklisted": "Kees 'nen angere, besjrievendje naam."
+       "mw-widgets-dateinput-placeholder-month": "JJJJ-MM"
 }
index bd20fa3..8de4353 100644 (file)
        "passwordreset-emailelement": "Nomme utente: \n$1\n\nPoula segretta temporannia: \n$2",
        "passwordreset-emailsentemail": "Se questo addresso de posta elettronnica o l'è associou a-a teu utença, alloa saiâ inviou un'e-mail pe rempostâ a poula segretta.",
        "passwordreset-emailsentusername": "Se gh'è un adreçço de posta elettronica associou con questo nomme utente, alloa saiâ inviou una email pe rempostâ a password.",
-       "passwordreset-emailsent-capture": "L'è stæto inviòu un'e-mail de reimpostaçion da poula segretta, o contegnuo o l'è riportòu chì appreuvo.",
-       "passwordreset-emailerror-capture": "L'è stæto generòu un'e-mail de reimpostaçion da poula segretta, riportà chì appreuvo. L'invio {{GENDER:$2|a l'utente}} o no l'è ariêscîo: $1",
        "passwordreset-emailsent-capture2": "L'email de rempostaçion da password {{PLURAL:$1|a l'è stæta inviâ|son stæte inviæ}}. {{PLURAL:$1|O nomme|L'elenco di nommi}} utente e password o l'è mostrou chì de sotta.",
        "passwordreset-emailerror-capture2": "Invio de email {{GENDER:$2|a l'utente}} non ariescio: $1. {{PLURAL:$3|O nomme|L'elenco di nommi}} utente e password o l'è mostrou chì de sotta.",
        "passwordreset-nocaller": "Un chi ciamma ti g'hæ da dâlo",
        "passwordreset-nodata": "No è stæto fornio ni un nomme utente ni un adreçço de posta elettronica",
        "changeemail": "Cangia o elimmina l'adresso e-mail",
        "changeemail-header": "Completa sto formulaio pe cangiâ o to adresso e-mail. Se ti veu rimeuve l'associaçion de quasesegge addresso e-mail da-a teu utensa, lascia io neuvo addresso e-mail veuo quande ti invii o formulaio.",
-       "changeemail-passwordrequired": "Saiâ necessaio insei a poula segretta pe confermâ a modiffica.",
        "changeemail-no-info": "Pe anâ direttamente a sta paggina, primma ti g'hæ da intrâ .",
        "changeemail-oldemail": "Addresso e-mail corrente:",
        "changeemail-newemail": "Noeuvo adresso e-mail",
        "undo-nochange": "Pâ che-a modiffica a sæ zà stæta anullâ.",
        "undo-summary": "Annullou a modiffica $1 de [[Special:Contributions/$2|$2]] ([[User talk:$2|discuscion]])",
        "undo-summary-username-hidden": "Anullou a modiffica $1 de un utente ascoso",
-       "cantcreateaccounttitle": "Non se peu registrâ l'utente",
        "cantcreateaccount-text": "A registrassion da questo addresso IP (<b>$1</b>) a l'è stæta bloccâ da [[User:$3|$3]].\n\nA raxon dæta a l'è ''$2''",
        "cantcreateaccount-range-text": "A registraçion da di addressi IP inte l'intervallo <strong>$1</strong>, ch'o  l'includde o teu (<strong>$4</strong>), a l'è stæta bloccâ da [[User:$3|$3]].\n\nA raxon dæta da $3 a l'è <em>$2</em>",
        "viewpagelogs": "Veddi i log relativi a 'sta paggina.",
        "emptyfile": "O file apen-a caregou pâ esee voeuo. Questo poriæ ese dovuo a un aro into nomme do file. Controlla se ti voeu davei caregâ sto file.",
        "windows-nonascii-filename": "Questo wiki o no supporta di nommi de file con di caratteri speciali.",
        "fileexists": "Un papê con sto nomme o l'existe za, pe piaxei danni 'n'euggiâ a <strong>[[:$1]]</strong> se no ti t'ê seguo de voeilo cangiâ.\n[[$1|thumb]]",
-       "filepageexists": "A pagina de descriçion de questo file aq l'è za stæta creâ a l'adreçço <strong>[[:$1]]</strong>, sciben che no ghe segge ancon un file con questo nomme. A descriçion de l'oggetto inseia in fase de caregamento a no l'appariâ in scia pagina de descriçion. Pe fâ scì che l'oggetto o comparisce in scia pagina de descriçion, saiâ necessaio modificala manualmente.\n[[$1|thumb]]",
+       "filepageexists": "A pagina de descriçion de questo file a l'è za stæta creâ a l'adreçço <strong>[[:$1]]</strong>, sciben che no ghe segge ancon un file con questo nomme. A descriçion de l'oggetto inseia in fase de caregamento a no l'appariâ in scia pagina de descriçion. Pe fâ scì che l'oggetto o comparisce in sciâ pagina de descriçion, saiâ necessaio modificala manualmente.\n[[$1|thumb]]",
        "fileexists-extension": "Un file co-in nomme scimile a questo o l'esiste za: [[$2|thumb]]\n* Nomme do file caregou: <strong>[[:$1]]</strong>\n* Nomme do file existente: <strong>[[:$2]]</strong>\nTi voeu miga çerne un nomme ciu caratteristego?",
        "fileexists-thumbnail-yes": "O file caregou o pâ ese una miniatua ''(thumbnail)''. [[$1|thumb]]\nVerifica, pe confronto, il file <strong>[[:$1]]</strong>.\nSe se tratta da mæxima inmaggine, inte dimenscioin originale, no l'è necessaio caregâne un'atra in miniatua.",
        "file-thumbnail-no": "O nomme do file comença con <strong>$1</strong>; pâ ch'o segge un'inmaggine de dimenscioin redute ''(miniatua)''.\nSe ti dispon-i del'immaggine inta risoluçion originale, carreghila. Sedunque, pe piaxei, cangighe o nomme.",
index 041c73f..74b2357 100644 (file)
        "passwordreset-emailelement": "نام کاربری: \n$1\n\nگذرواژهٔ موقت: \n$2",
        "passwordreset-emailsentemail": "اگر نشانی پست الکترونیکی که وارد کردید برای حساب کاربریتان ثبت شده باشد، یک نامهٔ بازنشانی گذرواژه به آن فرستاده می‌شود.",
        "passwordreset-emailsentusername": "اگر نشانی پست الکترونیکی مرتبطی موجود باشد، یک نامه برای بازنشانی گذرواژه به آن ارسال خواهد شد.",
-       "passwordreset-emailsent-capture": "یک ایمیل بازنشانی که در پایین نمایش داده شده، فرستاده شده است.",
-       "passwordreset-emailerror-capture": "ایمیل بازنشانی، که در زیر نمایش داده شده، ایجاد شد، ولی ارسال آن به {{GENDER:$2|کاربر}} موفقیت‌آمیز نبود: $1",
        "changeemail": "تغییر یا حذف نشانی ایمیل",
        "changeemail-header": "برای تغییر ایمیلتان این فرم را کامل کنید. برای حذف ایملیتان کافی است بخش ایمیل را خالی رها کنید و فرم را ارسال کنید.",
-       "changeemail-passwordrequired": "برای تائید این تغییر باید گذرواژه‌تان را وارد کنید.",
        "changeemail-no-info": ".برای دسترسی مستقیم به این صفحه شما باید به سیستم وارد شده باشید",
        "changeemail-oldemail": ":نشانی ایمیل ایسة هؤمة",
        "changeemail-newemail": ":نشانی ایمیل تازة",
        "undo-nochange": "به نظر می‌رسد ویرایش از پیش واگردانی شده است.",
        "undo-summary": "خنثی‌سازی ویرایش $1 توسط [[Special:Contributions/$2|$2]] ([[User talk:$2|بحث]])",
        "undo-summary-username-hidden": "خنثی‌سازی نسخهٔ $1 به دست یک کاربر پنهان‌شده",
-       "cantcreateaccounttitle": "نمی‌توان حساب باز کرد",
        "cantcreateaccount-text": "امكان ساختن حساب کاربری از این این نشانی آی‌پی ('''$1''') توسط [[User:$3|$3]] سلب شده است.\n\nدلیل ارائه شده توسط $3 چنین است: $2",
        "cantcreateaccount-range-text": "ایجاد حساب از آدرس آی‌پی در مجموعه‌ی <strong>$1</strong>، که شامل آدرس آی‌پی شما (<strong>$4</strong>) است، توسط [[User:$3|$3]] متوقف شده‌است.\nدلیل ارائه شده توسط $3، $2 است.",
        "viewpagelogs": "نمایش سیاهه‌های این صفحه",
index 319770c..a59c30b 100644 (file)
        "passwordreset-emailelement": "Naudotojo vardas: \n$1\n\nLaikinas slaptažodis: \n$2",
        "passwordreset-emailsentemail": "Jeigu šis el. pašto adresas yra susietas su jūsų paskyra, tada slaptažodžio atkūrimo laiškas bus išsiųstas.",
        "passwordreset-emailsentusername": "Jeigu buvo el. paštas susietas su šiuo naudotojo vardu, tai slaptažodžio atkūrimo el. laiškas bus išsiųstas.",
-       "passwordreset-emailsent-capture": "Slaptažodžio priminimo laiškas bus išsiųstas, toks koks parodytas.",
-       "passwordreset-emailerror-capture": "Priminimo elektroninis laiškas buvo sukurtas, toks, koks parodytas žemiau, bet pasiuntimas naudotojui buvo nesėkmingas: $1",
        "passwordreset-emailsent-capture2": "Slaptažodžio keitimo {{PLURAL:$1|el. laiškas buvo išsiųstas|el. laiškai buvo išsiųsti}}. {{PLURAL:$1|vartotojo vardas ir slaptažodis rodomi|vartotojų vardų ir slaptažodžių sąrašas rodomas}} žemiau.",
        "passwordreset-emailerror-capture2": "El. laiško siuntimas {{GENDER:$2|vartotojui}} nepavyko: $1 {{PLURAL:$3|vartotojo vardas ir slaptažodis rodomi|vartotojų vardų ir slaptažodžių sąrašas rodomas}} žemiau.",
        "passwordreset-nocaller": "Skambinantysis turi būti nurodytas",
        "passwordreset-nodata": "Vartotojo vardas ir el. paštas buvo nepateikti",
        "changeemail": "Pakeisti ar pašalinti el. pašto adresą",
        "changeemail-header": "Užpildykite šią formą, kad pakeistumėte savo el. pašto adresą. Jeigu norite pašalinti bet kurio el. pašto adreso susiejimą su savo paskyra, palikite naujojo el. pašto adreso lauką tuščią, kai pateiksite formą.",
-       "changeemail-passwordrequired": "Jums reikės įvesti savo slaptažodį, kad patvirtintumėte šį pakeitimą.",
        "changeemail-no-info": "Jūs turite būti prisijungęs, kad pasiektumėte puslapį tiesiogiai.",
        "changeemail-oldemail": "Dabartinis el. pašto adresas:",
        "changeemail-newemail": "Naujas el. pašto adresas:",
        "undo-nochange": "Panašu, kad keitimas jau buvo atšauktas.",
        "undo-summary": "Atšauktas [[Special:Contributions/$2|$2]] ([[User talk:$2|Aptarimas]] | [[Special:Contributions/$2|{{MediaWiki:Contribslink}}]]) keitimas ($1 versija)",
        "undo-summary-username-hidden": "Atmesti versiją $1, atliktą paslėpto naudotojo",
-       "cantcreateaccounttitle": "Paskyrų kūrimas negalimas",
        "cantcreateaccount-text": "Paskyrų kūrimą iš šio IP adreso ('''$1''') užblokavo [[User:$3|$3]].\n\n$3 nurodyta priežastis yra ''$2''",
        "cantcreateaccount-range-text": "Naudotojas [[User:$3|$3]] nustatė draudimą kurti paskyras iš IP adresų plotmės <strong>$1</strong>, į kurią patenka ir jūsiškis IP adresas (<strong>$4</strong>).",
        "viewpagelogs": "Rodyti šio puslapio specialiuosius veiksmus",
index b20432e..ecd1cf0 100644 (file)
        "passwordreset-emailtitle": "Konta informācija {{SITENAME}}",
        "passwordreset-emailelement": "Lietotājvārds: \n$1\n\nPagaidu parole: \n$2",
        "passwordreset-emailsentemail": "Paroles atiestatīšanas e-pasts ir nosūtīts.",
-       "passwordreset-emailsent-capture": "Atgādinājuma e-pasta ziņojums ir nosūtīts, tas parādīts zemāk.",
-       "passwordreset-emailerror-capture": "Atgādinājuma e-pasta ziņojums tika izveidots, tas parādīts zemāk, bet nosūtīšana lietotājam neizdevās: $1",
        "passwordreset-nosuchcaller": "Izsaucējs nepastāv: $1",
        "passwordreset-invalideamil": "Nederīga e-pasta adrese",
        "changeemail": "Mainīt e-pasta adresi",
        "undo-failure": "Šo labojumu nevar atcelt, jo ir veikti nozīmīgi labojumi vēl pēc šī labojuma izdarīšanas.",
        "undo-norev": "Šo izmaiņu nevar atcelt, jo tādas nav vai tā ir izdzēsta.",
        "undo-summary": "Atcēlu [[Special:Contributions/$2|$2]] ([[User talk:$2|Diskusija]]) izdarīto izmaiņu $1",
-       "cantcreateaccounttitle": "Nevar izveidot dalībnieku",
        "cantcreateaccount-text": "[[Lietotājs:$3|$3]] ir bloķējis lietotāja izveidošanu no šīs IP adreses ('''$1''').\n\n$3 norādītais iemesls ir ''$2''",
        "viewpagelogs": "Apskatīt ar šo lapu saistītos reģistru ierakstus",
        "nohistory": "Šai lapai nav pieejama versiju hronoloģija.",
index f7332f9..e02a91c 100644 (file)
@@ -22,7 +22,8 @@
                        "सरोज कुमार ढकाल",
                        "Bijay chaurasia",
                        "Tulsi Bhagat",
-                       "Macofe"
+                       "Macofe",
+                       "राम प्रसाद जोशी"
                ]
        },
        "tog-underline": "लिङ्कके रेखाङ्कित करी:",
        "passwordreset-emailtext-user": "प्रयोक्ता $1 {{अन्तर्जाल}} पर अहाँक खाता विवरणक {{SITENAME}} लेल फेरसँ ($4) आग्रह केने छथि। ई प्रयोक्ता {{PLURAL:$3|खाता अछि|खाता सभ अछि}} ऐ ई-पत्र संकेतसँ जुड़ल: $2\n{{PLURAL:$3| ई अस्थायी कूटशब्द|ई सभ अस्थायी कूटशब्द}} खतम भऽ जाएत {{PLURAL:$5|एक दिन|$5 दिन}} मे।\nअहाँ सम्प्रवेश करू आ एकटा नव कूटशब्द आब चुनू। जँ कियो दोसर ई आग्रह केने छथि, वा जँ अहाँकेँ अपन मूल कूटशब्द मोन पड़ि गेल अछि, आ अहाँ आब ओइ कूटशब्दकेँ नै बदलऽ चाहै छी, अहाँ ऐ संदेशकेँ बिसरि सकै छी आ अपन पुरान कूटशब्दक प्रयोग जारी राखि सकै छी।",
        "passwordreset-emailelement": "प्रयोक्ता: \n$1\n\nअस्थायी कूटशब्द: \n$2",
        "passwordreset-emailsentemail": "एकटा ई-पत्र मोन पाड़बा लेल पठाओल गेल अछि।",
-       "passwordreset-emailsent-capture": "एकटा स्मरण ई-पत्र पठाएल गेल अछि, जे नीचाँ देखाएल अछि।",
-       "passwordreset-emailerror-capture": "एकटा स्मरण ई-पत्र बनाएल गेल अछि, जे नीचाँ देखाएल अछि, मुदा प्र्योक्ताकेँ एकरा पठेबाक प्रयास विफल भेल: $1",
        "changeemail": "ई-मेल पता परिवर्तित करी",
        "changeemail-header": "अपन ईमेल पता परिवर्तन हेतु एकरा पुरा करी। यदि अहाँ अपन वर्तमान ईमेल पता हटाबैलेल चाहैत छी, तँ एकरा खाली छोडि दी आ एकरा भेजी।",
        "changeemail-no-info": "अहाँक ई पन्नाक सोझे प्रयोग करबालेल सम्प्रवेशित हुअए पडत।",
        "undo-nochange": "ऐना लगया की ई सम्पादन कें पहील से पूर्ववत करई देन अछि।",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|वार्ता]])द्वारा कएल अन्तर $1 के पूर्ववत कएलक",
        "undo-summary-username-hidden": "नुकाएल गेल प्रयोक्ताद्वारा केल गेल परिवर्तन $1 के पूर्ववत केल गेल",
-       "cantcreateaccounttitle": "खाता नै बना सकल",
        "cantcreateaccount-text": "(<strong>$1</strong>) अनिकेत पतासँ खाता निर्माण प्रतिबन्धित कएल गेल [[User:$3|$3]]।\n$3 द्वारा देल कारण अछि ''$2''",
        "cantcreateaccount-range-text": "<strong>$1</strong> के श्रेणी में आबई वाला आई॰पी पता सऽ, जएमें आहाँ कें आई॰पी पता (<strong>$4</strong>) शामिल अछि, नया खाता के रचना [[User:$3|$3]] द्वारा अवरोधित केल गेल अछि। \n\n$3 द्वारा देल गेल कारण अछि: \"$2\"",
        "viewpagelogs": "ई पन्नाक वृत्तलेखसभ देखी",
        "sqlite-has-fts": "$1 पूर्ण-पाठ खोज सहायता युक्त",
        "sqlite-no-fts": "$1 बिन पूर्ण-पाठ खोज सहायताक",
        "logentry-delete-delete": "$1 पृष्ठ $3 {{GENDER:$2|मेटौलक}}",
-       "logentry-delete-restore": "$1 {{लिंग:$2|restored}} page $3",
+       "logentry-delete-restore": "$1 {{GENDER:$2|restored}} page $3",
        "logentry-delete-event": "$1 {{लिंग:$2|changed}} एकर दृश्य{{PLURAL:$5| एकटा वृत्तलेख|$5 वृत्तलेख}}  $3: $4 केँ",
        "logentry-delete-revision": "$1 {{लिंग:$2|changed}} एकर दृश्य{{PLURAL:$5| एकटा संशोधन|$5 संशोधन}}  पन्ना $3: $4 पर",
-       "logentry-delete-event-legacy": "$1 {{लिंग:$2|changed}}  $3 पर वृत्तलेख दृश्य",
-       "logentry-delete-revision-legacy": "$1 {{लिंग:$2|changed}}  $3 पर वृत्तलेख संशोधन",
+       "logentry-delete-event-legacy": "$1 {{GENDER:$2|changed}}  $3 पर वृत्तलेख दृश्य",
+       "logentry-delete-revision-legacy": "$1 {{GENDER:$2|changed}}  $3 पर वृत्तलेख संशोधन",
        "logentry-suppress-delete": "$1 {{लिंग:$2|दबाएल}} page $3",
        "logentry-suppress-event": "$1 चोरिसँ {{लिंग:$2|changed}} एकर दृश्य{{PLURAL:$5| एकटा वृत्तलेख|$5 वृत्तलेख}}  $3: $4 पर",
        "logentry-suppress-revision": "$1 चोरिसँ {{लिंग:$2|changed}} एकर दृश्य{{PLURAL:$5| एकटा संशोधन|$5 संशोधन}}  $3: $4 पर",
-       "logentry-suppress-event-legacy": "$1 नुका कऽ {{लिंग:$2|changed}}  $3 पर वृत्तलेख दृश्य",
-       "logentry-suppress-revision-legacy": "$1 नुका कऽ {{लिंग:$2|changed}}  $3 पर संशोधन दृश्य",
+       "logentry-suppress-event-legacy": "$1 नुका क {{GENDER:$2|परिवर्तन}}  $3 पर वृत्तलेख दृश्य",
+       "logentry-suppress-revision-legacy": "$1 नुका कऽ {{GENDER:$2|changed}}  $3 पर संशोधन दृश्य",
        "revdelete-content-hid": "सामिग्री नुकाएल",
        "revdelete-summary-hid": "नुकाएल सारांश सम्पादन",
        "revdelete-uname-hid": "प्रयोक्तानाम नुकाएल",
        "logentry-import-interwiki": "$1 {{GENDER:$2|आयात केल गेल}} $3 कोनो और विकि सँ",
        "logentry-merge-merge": "$1 {{GENDER:$2|विलय केल गेल}} $3 के $4 में (संशोधन $5 धरि)",
        "logentry-move-move": "$1 हटाएल पन्ना $3 सँ $4",
-       "logentry-move-move-noredirect": "$1 {{लिंग:$2|हटाएल}} पन्ना $3 सँ $4 घुमौआकेँ बिना छोड़ने",
-       "logentry-move-move_redir": "$1 {{लिंग:$2|हटाएल}} पन्ना $3 सँ $4 घुमौआक अतिरिक्त",
+       "logentry-move-move-noredirect": "$1 {{GENDER:$2|हटाएल}} पन्ना $3 सँ $4 घुमौआकेँ बिना छोड़ने",
+       "logentry-move-move_redir": "$1 {{GENDER:$2|हटाएल}} पन्ना $3 सँ $4 घुमौआक अतिरिक्त",
        "logentry-move-move_redir-noredirect": "$1 {{लिंग:$2|हटाएल}} पन्ना $3 सँ $4 घुमौआक अतितिक्त घुमौआकेँ बिना छोड़ने",
        "logentry-patrol-patrol": "$1 {{GENDER:$2|चिन्हित}} संशोधन $4 $3 पन्नाक निरीक्षित",
        "logentry-patrol-patrol-auto": "$1 स्वतः {{GENDER:$2|चिन्हित}} संशोधन $4 $3 पन्नाक निरीक्षित",
-       "logentry-newusers-newusers": "$1 {{लिंग:$2|बनाएल}} एकटा प्रयोक्ता खाता",
+       "logentry-newusers-newusers": "$1 {{GENDER:$2|बनाएल}} एकटा प्रयोक्ता खाता",
        "logentry-newusers-create": "प्रयोगकर्ता खाता $1 {{GENDER:$2|बनाएल}} गेल",
-       "logentry-newusers-create2": "$1 {{लिंग:$2|बनाएल}} {{लिंग:$4|एकटा प्रयोक्ता खाता}} $3",
+       "logentry-newusers-create2": "$1 {{GENDER:$2|बनाएल}} {{GENDER:$4|एकटा प्रयोक्ता खाता}} $3",
        "logentry-newusers-byemail": "$1 द्वारा प्रयोक्ता खाता $3 {{GENDER:$2|बनाओल}} गेल आ कूटशब्द ई-पत्र द्वारा भेजल गेल",
-       "logentry-newusers-autocreate": "खाता $1 छल {{लिंग:$2|बनाएल}} स्वतः",
+       "logentry-newusers-autocreate": "खाता $1 छल {{GENDER:$2|बनाएल}} स्वतः",
        "logentry-upload-upload": "$1 {{GENDER:$2|ए}} $3 अपलोड केलक",
        "log-name-tag": "ट्याग लग",
        "rightsnone": "(कोनो नै)",
index b180b5f..2cc972a 100644 (file)
        "passwordreset-emailtitle": "Detil akun nang {{SITENAME}}",
        "passwordreset-emailelement": "Jeneng panganggo: \n$1\n\nTembung sandhi sauntara: \n$2",
        "passwordreset-emailsentemail": "Imel nggo nyetel maning tembung sandhi uwis dikirim.",
-       "passwordreset-emailsent-capture": "Imel kanggo nyetel maning tembung sandhi uwis dikirim, kaya sing ditidokna nang ngisor kiye.",
-       "passwordreset-emailerror-capture": "Imel nggo nyetel maning tembung sandhi uwis digawe, kaya sing ditidokna nang ngisor kiye, ningen gole ngirim maring {{GENDER:$2|panganggo}} ora teyeng: $1",
        "changeemail": "Ganti alamat imel",
        "changeemail-header": "Ganti alamat imel-e akun",
        "changeemail-no-info": "Rika kudu mlebu log kanggo ngakses kaca kiye sacara langsung.",
        "subject": "Subyek/judhul:",
        "minoredit": "Kiye suntingan cilik",
        "watchthis": "Awasi kaca kiyé",
-       "savearticle": "Simpen",
+       "savearticle": "Terbitna Kaca",
        "preview": "Pra tayang",
        "showpreview": "Pra tayang",
        "showdiff": "Ndeleng bedané",
        "undo-failure": "Suntingan kiye ora teyeng dibatalna jalaran ana konflik panyuntingan antara.",
        "undo-norev": "Suntingan kiye ora teyeng dibatalna jalaran wis ora ana utawa anu wis dibusek.",
        "undo-summary": "Mbatalna revisi $1 sekang [[Special:Contributions/$2|$2]] ([[User talk:$2|dopokan]])",
-       "cantcreateaccounttitle": "Ora teyeng gawe akun",
        "cantcreateaccount-text": "Ngawe akun sekang alamat IP kiye ('''$1''') wis diblokir nang [[User:$3|$3]].\n\nAlesane miturut $3 yakuwe ''$2''",
        "viewpagelogs": "Deleng log-e kaca kiye",
        "nohistory": "Ora ana sajarah panyuntingan kanggo kaca kiye.",
index e1722ba..94699ba 100644 (file)
        "category-file-count-limited": "Anatin'ity sokajy ity ireo rakitra ireo. ($1 no aseho) {{PLURAL:}}",
        "listingcontinuesabbrev": " manaraka.",
        "index-category": "pejy voasokajy",
-       "noindex-category": "Pejy tsy voasikajy",
+       "noindex-category": "Pejy tsy voatondro",
        "broken-file-category": "Pejy misy rohin-drakitra tapaka",
        "about": "Mombamomba",
        "article": "Votoatin'ny pejy",
        "passwordreset-emailtext-user": "Nisy mpikambana mitondra anarana $1 eo amin'i {{SITENAME}} nangataka fampatsiahivana mikasika ny kaontinao eo amin'i {{SITENAME}} ($4). Manana io adiresy imailaka {{PLURAL:$3|io kaontim-pikambana io|ireo kaontim-pikambana ireo}} :\n\n$2\n\nHitsahatra afaka {{PLURAL:$5|iray|$5}} andro {{PLURAL:$3|io|ireo}} tenimiafina {{PLURAL:$3|io|ireo}}. Mila miditra dien'izao ianao izao ary mifidy tenimiafina vaovao. Raha tsy avy aminao ity hataka ity na efa nahatadidy ny tenimiafinao taloha ianao, ary raha tsy tianao hovaina intsony ilay tenimiafinao, dia azonao tsy raharahiana ity hafatra ity ary mampiasa ny tenimiafinao taloha.",
        "passwordreset-emailelement": "Anaram-pikambana : \n$1\n\nTenimiafina miserana : \n$2",
        "passwordreset-emailsentemail": "Lasa ny mailaka famerenana tenimiafina.",
-       "passwordreset-emailsent-capture": "Lasa ilay mailaka famerenana tenimiafina, izay aseho eo ambany.",
-       "passwordreset-emailerror-capture": "Nosoratana ilay mailaka famerenana tenimiafina, izay aseho eo ambany, fa tsy tafalefa tany amin'ilay mpikambana ilay izy : $1{{GENDER:$2}}",
        "changeemail": "Hanova ny adiresy imailaka",
        "changeemail-header": "Hanova ny adiresy imailak'ilay kaonty",
        "changeemail-no-info": "Mila tafiditra ianao vao avaka mijery ity pejy ity.",
        "undo-nochange": "Hoatry ny efa nofoanana ilay fanovana.",
        "undo-summary": "Niala ny fanovàna $1 nataon'i [[Special:Contributions/$2|$2]] ([[User talk:$2|resaho]])",
        "undo-summary-username-hidden": "Namafa ny famerenana $1 nataom-pikambana afenina",
-       "cantcreateaccounttitle": "Tsy afaka manokatra kaonty ianao.",
        "cantcreateaccount-text": "Voasakan'i [[User:$3|$3]] ny fanokafana kaonty avy amin'ity adiresy IP (<b>$1</b>)\n\n''$2'' ny antony.",
        "cantcreateaccount-range-text": "Nosakanan'i [[User:$3|$3]] ny fanokafana kaonty avy amin'ny adiresy IP ao amin'ny elanelana <strong>$1</strong> izay ahitana ny adiresy IP-nao (<strong>$4</strong>).",
        "viewpagelogs": "Hijery ny fanovan'ity pejy ity",
index 6780a3f..868df89 100644 (file)
        "passwordreset-emailtext-user": "Sasaurang (mungkin Sanak, dari alamaik IP $1) mamintak parubahan kato sandi untuak {{SITENAME}} ($4).\n{{PLURAL:$3|Akun}} barikuik takaik jo alamaik surel ko:\n\n$2\n\n{{PLURAL:$3|Sandi samantaro}} barikuik akan habih masonyo dalam {{PLURAL:$5|$5 ari}}.\nSanak harus masuak dan mamiliah sandi baru. Jikok urang lain mambuek pamintaan ko atau jikok Sanak ingek sandi awal dan indak nio maubahnyo, Sanak dapek mangacuahkan pasan ko dan taruih manggunoan kato sandi lamo.",
        "passwordreset-emailelement": "Namo pangguno: \n$1\n\nSandi samantaro: \n$2",
        "passwordreset-emailsentemail": "Surel parubahan kato sandi alah dikirim.",
-       "passwordreset-emailsent-capture": "Surel parubahan kato sandi alah dikirim, nan nampak di bawah ko.",
-       "passwordreset-emailerror-capture": "Surel parubahan kato sandi nan ditampilan di bawah, alah dibuek, tapi pangirimannyo ka {{GENDER:$2|pangguno}} gagal: $1",
        "changeemail": "Tuka alamaik surel.",
        "changeemail-header": "Ganti alamaik surel.",
        "changeemail-no-info": "Sanak harus masuak log untuak mangakses laman ko.",
        "minoredit": "Suntiangan ketek",
        "watchthis": "Pantau laman ko",
        "savearticle": "Simpan",
+       "publishpage": "Tabikan laman",
+       "publishchanges": "Tabikan parubahan",
        "preview": "Caliak",
        "showpreview": "Pratonton",
        "showdiff": "Parubahan",
        "undo-failure": "Suntiangan ko indak dapek dibatalan dek konflik panyuntiangan antaro.",
        "undo-norev": "Suntiangan ko indak dapek dibatalan dek laman indak ditamukan atau lah dihapuih.",
        "undo-summary": "Mambatalan revisi $1 oleh [[Special:Contributions/$2|$2]] ([[User talk:$2|maota]])",
-       "cantcreateaccounttitle": "Indak dapek mambuek akun",
        "cantcreateaccount-text": "Mambuek akun dari alamat IP ko ('''$1''') alah diblok jo [[User:$3|$3]].\n\nAlasan nan diagiah jo $3 adolah ''$2''",
        "viewpagelogs": "Caliak log untuak laman ko",
        "nohistory": "Indak ado sajarah panyuntiangan untuak laman ko",
index 087ea59..893d69c 100644 (file)
        "passwordreset-emailelement": "Корисничко име: \n$1\n\nПривремена лозинка: \n$2",
        "passwordreset-emailsentemail": "Ако ова е регистрираната е-пошта поврзана со вашата сметка, тогаш ќе ви биде испратено писмо за задавање на нова лозинка.",
        "passwordreset-emailsentusername": "Ако има соодветна регистрирана е-пошта поврзана со ова корисничко име, тогаш ќе ви биде испратена порака за промена на лозинката.",
-       "passwordreset-emailsent-capture": "Испратено е писмо за измена на лозинката (прикажано подолу).",
-       "passwordreset-emailerror-capture": "Создадено е писмо за измена на лозинката (прикажано подолу), но не успеав да го испратам на {{GENDER:$2|корисникот}}: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|Е-поштата за задавање на нова лозинка|Е-поштата за задавање на нови лозинки}} е испратена. Подолу е {{PLURAL:$1|е прикажано корисничкото име и лозинката|прикажан список на кориснички имиња и лозинки}}.",
        "passwordreset-emailerror-capture2": "Испраќањето е-пошта на {{GENDER:$2|корисникот}} не успеа: $1 Подолу е {{PLURAL:$3|прикажано корисничкото име и лозинката|прикажан список на кориснички имиња и лозинки}}.",
        "passwordreset-nocaller": "Мора да се укаже повикувач",
        "passwordreset-nodata": "Немате укажано ни корисничко име, ни е-пошта.",
        "changeemail": "Смени или отстрани е-пошта",
        "changeemail-header": "Пополнете го образецов за да ја смените е-поштата. Ако сакате да ја отстраните адресата од вашата сметка, оставете го празно полето за нова е-пошта.",
-       "changeemail-passwordrequired": "Ќе треба да ја внесете лозинката за да ја потврдите измената.",
        "changeemail-no-info": "Мора да бидете најавени ако сакате да имате директен пристап до оваа страница.",
        "changeemail-oldemail": "Тековна е-пошта:",
        "changeemail-newemail": "Нова е-пошта:",
        "undo-nochange": "Се чини дека измената (уредувањето) е веќе вратена.",
        "undo-summary": "Откажано уредувањето $1 на уредникот [[Special:Contribs/$2|$2]] ([[User talk:$2|разговор]])",
        "undo-summary-username-hidden": "Поништи ја преработката $1 на скриен корисник",
-       "cantcreateaccounttitle": "Не може да се создаде корисничка сметка",
        "cantcreateaccount-text": "Создавањето на корисничка сметка од оваа IP-адреса ('''$1''') е блокирано од страна на [[User:$3|$3]].\n\nОбразложението дадено од страна на $3 е ''$2''",
        "cantcreateaccount-range-text": "Создавањето на сметки од IP-адреси во опсегот <strong>$1</strong> каде спаѓа вашата IP-адреса (<strong>$4</strong>) е блокирано од корисникот [[User:$3|$3]].\n\n$3 ја наведе следнава причина: <em>$2</em>",
        "viewpagelogs": "Преглед на дневници за оваа страница",
        "uploadstash-errclear": "Чистењето на податотеките не успеа.",
        "uploadstash-refresh": "Превчитај го списокот на податотеки",
        "uploadstash-thumbnail": "погл. минијатура",
+       "uploadstash-exception": "Не можев да го складирам подигнатото во складиштето ($1): „$2“.",
        "invalid-chunk-offset": "Неважечка појдовна точка",
        "img-auth-accessdenied": "Оневозможен пристап",
        "img-auth-nopathinfo": "Недостасува PATH_INFO.\nВашиот опслужувач не е нагоден за да ја предаде оваа информација.\nМожеби се заснова на CGI, и така не подржува img_auth.\nПогл. https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization.",
        "undeletehistorynoadmin": "Оваа статија е избришана. Причината за бришењето е наведена подолу,\nзаедно со информации за корисникот кој ја уредувал страницата пред бришењето. Целиот текст\nод избришаните верзии е достапен само за администраторите.",
        "undelete-revision": "Избришана преработка на $1 (од $4, во $5) од уредникот $3:",
        "undeleterevision-missing": "Грешна или непостоечка преработка.\nМожеби имате лоша врска, преработката била обновена или избришана од архивата.",
+       "undeleterevision-duplicate-revid": "Не можев да повратам {{PLURAL:$1|една преработка|$1 преработки}} бидејќи {{PLURAL:$1|нејзината|нивните}} <code>rev_id</code> се веќе зафатени.",
        "undelete-nodiff": "Не постои постара преработка.",
        "undeletebtn": "Врати",
        "undeletelink": "погледај/врати",
        "undeletedrevisions": "{{PLURAL:$1|1 измена е обновена|$1 измени се обновени}}",
        "undeletedrevisions-files": "{{PLURAL:$1|1 измена|$1 измени}} и {{PLURAL:$2|1 податотека|$2 податотеки}} се вратени",
        "undeletedfiles": "{{PLURAL:$1|1 податотека е вратена|$1 податотеки се вратени}}",
-       "cannotundelete": "Враќањето не успеа:\n$1",
+       "cannotundelete": "Враќањето не успеа делумно или целосно:\n$1",
        "undeletedpage": "'''$1 беше обновена'''\n\nПогледнете го [[Special:Log/delete|дневникот на бришења]] за попис на претходни бришења и обновувања.",
        "undelete-header": "Списокот на неодамна избришани страници ќе го најдете на [[Special:Log/delete|дневникот на бришења]].",
        "undelete-search-title": "Пребарување на избришани страници",
        "sp-contributions-newbies-sub": "За нови кориснички сметки",
        "sp-contributions-newbies-title": "Придонеси на нови корисници",
        "sp-contributions-blocklog": "Дневник на блокирања",
-       "sp-contributions-suppresslog": "притаени придонеси на корисникот",
-       "sp-contributions-deleted": "избÑ\80иÑ\88ани ÐºÐ¾Ñ\80иÑ\81ниÑ\87ки Ð¿Ñ\80идонеÑ\81и",
+       "sp-contributions-suppresslog": "притаени придонесите на {{GENDER:$1|корисникот|корисничката}}",
+       "sp-contributions-deleted": "избÑ\80иÑ\88ани Ð¿Ñ\80идонеÑ\81иÑ\82е Ð½Ð° {{GENDER:$1|коÑ\80иÑ\81никоÑ\82|коÑ\80иÑ\81ниÑ\87каÑ\82а}}",
        "sp-contributions-uploads": "подигања",
        "sp-contributions-logs": "дневници",
        "sp-contributions-talk": "разговор",
index 793c5ab..389d307 100644 (file)
        "passwordreset-emailelement": "ഉപയോക്തൃനാമം: \n$1\n\nതാത്കാലിക രഹസ്യവാക്ക്: \n$2",
        "passwordreset-emailsentemail": "താങ്കളുടെ അംഗത്വത്തിന് നൽകിയിട്ടുള്ള ഇമെയിൽ വിലാസം ഇതാണെങ്കിൽ,  രഹസ്യവാക്ക് പുനർസജ്ജീകരണ ഇമെയിൽ അയക്കുന്നതാണ്.",
        "passwordreset-emailsentusername": "ഈ ഉപയോക്തൃനാമത്തിന് ഒരു ഇമെയിൽ വിലാസം ചേർത്തിട്ടുണ്ടെങ്കിൽ,  രഹസ്യവാക്ക് പുനർസജ്ജീകരണ ഇമെയിൽ അയക്കുന്നതാണ്.",
-       "passwordreset-emailsent-capture": "രഹസ്യവാക്ക് പുനർസജ്ജീകരണ ഇമെയിൽ അയച്ചിട്ടുണ്ട്, അത് താഴെക്കൊടുക്കുന്നു.",
-       "passwordreset-emailerror-capture": "താഴെക്കൊടുത്തിരിക്കുന്ന, രഹസ്യവാക്ക് പുനർസജ്ജീകരണ ഇമെയിൽ സൃഷ്ടിക്കാനായെങ്കിലും, അത് {{GENDER:$2|ഉപയോക്താവിന്}} അയയ്ക്കുന്നത് പരാജയപ്പെട്ടു: $1",
        "changeemail": "ഇമെയിൽ വിലാസം മാറ്റുക അല്ലെങ്കിൽ നീക്കംചെയ്യുക",
        "changeemail-header": "താങ്കളുടെ ഇമെയിൽ വിലാസത്തിൽ മാറ്റംവരുത്താൻ ഈ ഫോം പൂരിപ്പിച്ചു നൽകുക.താങ്കളുടെ അംഗത്വവുമായി ഏതെങ്കിലുമൊരു ഇമെയിൽ വിലാസത്തിനുള്ള ബന്ധം ഒഴിവാക്കാൻ ഫോം പൂരിപ്പിക്കുമ്പോൾ പുതിയ ഇമെയിൽ വിലാസത്തിനുള്ള ഭാഗം ഒഴിച്ചിടുക.",
-       "changeemail-passwordrequired": "ഈ മാറ്റം സ്ഥിരീകരിക്കാൻ താങ്കളുടെ രഹസ്യവാക്ക് നൽകുക.",
        "changeemail-no-info": "ഈ താൾ നേരിട്ടു കാണുന്നതിന് താങ്കൾ ലോഗിൻ ചെയ്തിരിക്കണം.",
        "changeemail-oldemail": "ഇപ്പോഴത്തെ ഇമെയിൽ വിലാസം:",
        "changeemail-newemail": "പുതിയ ഇമെയിൽ വിലാസം:",
        "undo-nochange": "തിരുത്ത് മുമ്പേ തന്നെ ഒഴിവാക്കിയതായി കാണുന്നു.",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|സംവാദം]]) ചെയ്ത നാൾപ്പതിപ്പ് $1 നീക്കം ചെയ്യുന്നു",
        "undo-summary-username-hidden": "മറയ്ക്കപ്പെട്ട ഉപയോക്താവ് ചെയ്ത നാൾപ്പതിപ്പ് $1 തിരസ്കരിക്കുക",
-       "cantcreateaccounttitle": "അംഗത്വം സൃഷ്ടിക്കാൻ സാധിച്ചില്ല",
        "cantcreateaccount-text": "ഈ ഐ.പി. ('''$1''') വിലാസത്തിൽ നിന്നു അംഗത്വം സൃഷ്ടിക്കുന്നത് [[User:$3|$3]] നിരോധിച്ചിരിക്കുന്നു.\n\n$3 അതിനു കാണിച്ചിരിക്കുന്ന കാരണം ''$2'' ആണ്‌.",
        "cantcreateaccount-range-text": "താങ്കളുടെ ഐ.പി. വിലാസം (<strong>$4</strong>) ഉൾപ്പെടുന്ന <strong>$1</strong> എന്ന പരിധിയിലെ ഐ.പി. വിലാസങ്ങളിൽ നിന്ന് അംഗത്വമെടുക്കുന്നത് [[User:$3|$3]] തടഞ്ഞിരിക്കുകയാണ്.\n\n$3 നൽകിയിരിക്കുന്ന കാരണം <em>$2</em> എന്നാണ്",
        "viewpagelogs": "ഈ താളുമായി ബന്ധപ്പെട്ട രേഖകൾ കാണുക",
index 7f02a6c..305228d 100644 (file)
@@ -21,7 +21,8 @@
                        "Pizza1016",
                        "Macofe",
                        "Matma Rex",
-                       "Nemo bis"
+                       "Nemo bis",
+                       "Mbrt"
                ]
        },
        "tog-underline": "Garis bawah pautan:",
        "passwordreset-emailtext-user": "Pengguna $1 telah memohon supaya kata laluan diset semula untuk {{SITENAME}} anda ($4). {{PLURAL:$3|Akaun|Akaun-akaun}} pengguna yang berikut\ndikaitkan dengan alamat e-mel ini:\n\n$2\n\n{{PLURAL:$3|Kata|Kata-kata}} laluan sementara ini akan luput dalam masa $5 hari. Anda harus log masuk dan membuat kata laluan yang baru sekarang. Jika permohonan ini dibuat oleh orang lain, atau jika anda teringat kembali kata laluan asal anda dan anda tidak lagi berhasrat untuk mengubahnya, anda boleh mengabaikan pesanan ini dan terus menggunakan kata laluan lama anda.",
        "passwordreset-emailelement": "Nama pengguna: \n$1\n\nKata laluan sementara: \n$2",
        "passwordreset-emailsentemail": "Jika ini ialah alamat e-mel yang terdaftar untuk akaun anda, maka e-mel set semula kata laluan akan dihantar.",
-       "passwordreset-emailsent-capture": "E-mel set semula kata laluan telah dihantar, seperti yang dipaparkan di bawah.",
-       "passwordreset-emailerror-capture": "E-mel set semula kata laluan telah dihasilkan, seperti yang dipaparkan di bawah, tetapi tidak berjaya dihantar kepada {{GENDER:$2|pengguna}} berkenaan: $1",
        "changeemail": "Tukar atau padamkan alamat e-mel",
        "changeemail-header": "Lengkapkan borang ini untuk menukar alamat e-mel anda. Jika anda ingin memutuskan sebarang hubungan alamat e-mel daripada akaun anda, biarkan ruangan alamat e-mel kosong ketika menghantar borang.",
-       "changeemail-passwordrequired": "Anda akan dikehendaki memasukkan kata laluan untuk mengesahkan perubahan ini.",
        "changeemail-no-info": "Anda hendaklah log masuk terlebih dahulu untuk mencapai laman ini secara terus.",
        "changeemail-oldemail": "Alamat e-mel sekarang:",
        "changeemail-newemail": "Alamat e-mel baru:",
        "subject": "Perkara:",
        "minoredit": "Ini adalah suntingan kecil",
        "watchthis": "Pantau laman ini",
-       "savearticle": "Simpan",
+       "savearticle": "Paparkan Laman",
        "publishpage": "Terbitkan",
        "publishchanges": "Terbit perubahan",
        "preview": "Pralihat",
        "undo-nochange": "Suntingan itu nampaknya sudah dibatalkan.",
        "undo-summary": "Membatalkan semakan $1 oleh [[Special:Contributions/$2|$2]] ([[User talk:$2|Perbincangan]])",
        "undo-summary-username-hidden": "Buat asal semakan $1 oleh pengguna tersembunyi",
-       "cantcreateaccounttitle": "Akaun tidak dapat dibuka",
        "cantcreateaccount-text": "Pembukaan akaun daripada alamat IP ini (<b>$1</b>) telah disekat oleh [[User:$3|$3]].\n\nSebab yang diberikan oleh $3 ialah ''$2''",
        "cantcreateaccount-range-text": "Pembukaan akaun dari alamat-alamat IP dalam julat <strong>$1</strong>, termasuk alamat IP anda (<strong>$4</strong>), telah disekat oleh [[User:$3|$3]].\n\nSebab yang diberikan oleh $3 ialah <em>$2</em>",
        "viewpagelogs": "Lihat log bagi laman ini",
index 9cae000..21bf1d8 100644 (file)
        "minoredit": "အရေးမကြီးသော ​ပြင်​ဆင်​မှု ​ဖြစ်​သည်​",
        "watchthis": "ဤစာမျက်နှာကို စောင့်ကြည့်ရန်",
        "savearticle": "ဤစာမျက်နှာကို သိမ်းရန်",
+       "publishpage": "စာမျက်နှာကို လွှင့်တင်ရန်",
+       "publishchanges": "ပြောင်းလဲမှုများကို လွှင့်တင်ရန်",
        "preview": "နမူနာ",
        "showpreview": "န​မူ​နာ​ပြ​ရန်",
        "showdiff": "ပြင်​ဆင်​ထား​သည်​များ​ကို​ ပြရန်",
index 591bdec..d60887a 100644 (file)
        "edit-conflict": "Tlapatlaliztli yāōyōtōn",
        "edit-already-exists": "Ahmo mohuelīti mochīhua yancuīc zāzanilli.\nYe ia.",
        "content-model-javascript": "JavaScript",
-       "cantcreateaccounttitle": "Ahmo huelītih mochīhua cuentah",
        "cantcreateaccount-text": "[[User:$3|$3]] ōcquīxti cuentah tlachīhualiztli īpal inīn IP ('''$1''').\n\nĪxtlamatiliztli īpal $3 cah ''$2''",
        "viewpagelogs": "Tiquinttāz tlahcuilōlloh inīn zāzaniltechcopa",
        "nohistory": "Nicān ahmō oncah tlaīxtlapatlaliztlahtōllōtl.",
index a39cb81..c756f47 100644 (file)
        "passwordreset-emailelement": "Nomme utente: \n$1\n\nPassword temporanea: \n$2",
        "passwordreset-emailsentemail": "Si chesto fosse nu cunto e-mail suoccio a 'o cunto vuost, allora buò dicere ca se mannarrà na mmasciata e-mail pe' riabbià 'a password.",
        "passwordreset-emailsentusername": "Si esistesse nu cunto e-mail suòccio a stu nomme utente, allora se mannarrà na mmasciata pe' riabbià 'a password.",
-       "passwordreset-emailsent-capture": "Na mmasciata e-mail pe' riabbià 'a password è stata mannata, chista mmasciata 'a putite vedé ccà abbascio.",
-       "passwordreset-emailerror-capture": "Na mmasciata e-mail pe' riabbià 'a password è stata mannata, 'a putite vedé ccà abbascio, ma aita sapé ca nun s'è mannata a {{GENDER:$2|l'utente}} pecché c'è stato cocch'errore: $1",
        "passwordreset-emailsent-capture2": "L'email 'e reimpostazione d' 'a password {{PLURAL:$1|è stata mannata|so' state mannate}}. {{PLURAL:$1|'O nomme|L'elenco 'e nomme}} utente e password è mmustato ccà.",
        "passwordreset-emailerror-capture2": "'O mannà 'email {{GENDER:$2|a ll'utente}} guastaje: $1. {{PLURAL:$3|'O nomme|L'elenco 'e nomme}} utente e password se ffà vedé ccà.",
        "passwordreset-nocaller": "Nu chiammate s'avess'a dà",
        "passwordreset-nodata": "Nun è stato fornito né nomme utente né indirizzo 'e posta email",
        "changeemail": "Cagna o lèva l'indirizzo e-mail",
        "changeemail-header": "Ghienchete stu modulo pe' puté cagnà 'o indirizzo e-mail d' 'o vuosto. Si vuje vulite luvà e 'o scucchià l'associazione 'e cocche cunto mail d' 'o cunto vuosto, lassate 'o cunto e-mail nuovo abbacante quanno mannarrate stu modulo.",
-       "changeemail-passwordrequired": "Avit'a miette 'a password vuosto pe' dà a cunferma 'e stu cagnamiento.",
        "changeemail-no-info": "Avite 'a trasì ('o login) pe ffà l'acciesso a sta paggena direttamente.",
        "changeemail-oldemail": "Indirizzo email 'e mmò:",
        "changeemail-newemail": "Indirizzo e-mail nuovo:",
        "undo-nochange": "Pare c' 'o cagnamiento s'è già fatto turnà arreto.",
        "undo-summary": "Canciella 'o cagnamiento $1 'e [[Special:Contributions/$2|$2]] ([[User talk:$2|Chiàcchiera]])",
        "undo-summary-username-hidden": "Annullato 'o cagnamiento $1 pe n'utente annascunnuto",
-       "cantcreateaccounttitle": "Nun se può crià cunto",
        "cantcreateaccount-text": "'A riggistraziona è stata bloccata 'a l'utente [[User:$3|$3]] 'a st'innerizzo IP ('''$1''').\n\n'O mutivo dato 'a $3 è chistu ccà: ''$2''",
        "cantcreateaccount-range-text": "'A criazione 'e cunte 'a ll'indirizze int'o ntervallo <strong>$1</strong>, che cummiglia 'o vuosto (<strong>$4</strong>), è stata bloccata 'a l'utente [[User:$3|$3]].\n\n'O mutivo dato 'a $3 è chistu ccà: <em>$2</em>",
        "viewpagelogs": "Vide 'e log azzeccate a sta paggena",
        "log-action-filter-newusers": "Tipo e' criazione utenza:",
        "log-action-filter-patrol": "Tipo 'e verifica:",
        "log-action-filter-protect": "Tipo 'e protezione:",
-       "log-action-filter-rights": "Tipo 'e cagnamiento 'e deritte",
+       "log-action-filter-rights": "Tipo 'e cagnamiento 'e deritte:",
        "log-action-filter-suppress": "Tipo 'e suppressione:",
        "log-action-filter-upload": "Tipo 'e carreca:",
        "log-action-filter-all": "Tutte",
        "authprovider-confirmlink-ok-help": "Cuntinuà aropp'a fà veré 'e mmasciate 'errore 'e cullegamento.",
        "authprovider-resetpass-skip-label": "Passa 'a vacca",
        "authprovider-resetpass-skip-help": "Passa 'a vacca 'mpustazion' 'e password.",
-       "authform-nosession-login": "'O prucesso 'autenticazione iette buono, ma 'o navigatóre d' 'o tuojo nun \"s'arricuorda\" si site trasuto/a.",
-       "authform-nosession-signup": "'O cunto è stato criato buono, ma 'o navigatóre d' 'o tuojo nun \"s'arricuorda\" si site trasuto/a.",
+       "authform-nosession-login": "'O prucesso 'autenticazione iette buono, ma 'o navigatóre d' 'o tuojo nun \"s'arricuorda\" si site trasuto/a.\n\n$1",
+       "authform-nosession-signup": "'O cunto è stato criato buono, ma 'o navigatóre d' 'o tuojo nun \"s'arricuorda\" si site trasuto/a.\n\n$1",
        "authform-newtoken": "Token mancante. $1",
        "authform-notoken": "Token mancante",
        "authform-wrongtoken": "Token errato",
index 6332449..150527f 100644 (file)
        "passwordreset-emailelement": "Brukernavn: \n$1\n\nMidlertidig passord: \n$2",
        "passwordreset-emailsentemail": "Hvis denne epostadressen er koblet til din konto, så vil det bli sendt en epost om tilbakestilling av passord.",
        "passwordreset-emailsentusername": "Hvis det finnes en epostadresse knyttet til dette brukernavnet, vil en epost med informasjon om tilbakestilling av passord bli sendt.",
-       "passwordreset-emailsent-capture": "Passordtilbakestillingseposten vist under har blitt sendt ut.",
-       "passwordreset-emailerror-capture": "En passordtilbakestillingsepost ble laget, men det lyktes ikke å sende denne til {{GENDER:$2|brukeren}}: $1",
        "changeemail": "Endre eller fjerne epostadresse",
        "changeemail-header": "Fyll ut dette skjemaet for å bytte din epost-adresse. Hvis du vil fjerne epostadressen fra din konto, kan du la ny epostadresse-feltet være tomt når.",
-       "changeemail-passwordrequired": "Du må skrive inn passordet ditt for å bekrefte denne endringen.",
        "changeemail-no-info": "Du må være innlogget for å få direkte tilgang til denne siden.",
        "changeemail-oldemail": "Nåværende e-postadresse:",
        "changeemail-newemail": "Ny e-postadresse:",
        "undo-nochange": "Det ser ut til at redigeringen allerede er tilbakestilt.",
        "undo-summary": "Fjerner revisjon $1 av [[Special:Contributions/$2|$2]] ([[User talk:$2|diskusjon]])",
        "undo-summary-username-hidden": "Fjern revisjon $1 av en skjult bruker",
-       "cantcreateaccounttitle": "Kan ikke opprette konto",
        "cantcreateaccount-text": "Kontooppretting fra denne IP-adressen ('''$1''') har blitt blokkert av [[User:$3|$3]].\n\nGrunnen som ble oppgitt av $3 er ''$2''",
        "cantcreateaccount-range-text": "Opprettelsen av en brukerkonto fra IP-adresser i intervallet <strong>$1</strong>, som inneholder din IP-adresse (<strong>$4</strong>), er blitt blokkert av [[User:$3|$3]].\n\nÅrsaken angitt av $3 er <em>$2</em>",
        "viewpagelogs": "Vis logger for denne siden",
index 73f9631..6cd436a 100644 (file)
        "minoredit": "Blots lütte Ännern",
        "watchthis": "Op disse Siet oppassen",
        "savearticle": "Siet spiekern",
+       "publishpage": "Siet nee afspiekern",
+       "publishchanges": "ännerte Siet afspiekern",
        "preview": "Vörschau",
        "showpreview": "Vörschau wiesen",
        "showdiff": "Ünnerscheed wiesen",
        "undo-failure": "Kunn de Siet nich op de vörige Version trüchdreihn. De Afsnitt is twischendör al wedder ännert worrn.",
        "undo-norev": "De Ännern kunn nich trüchdreiht warrn, de gifft dat nich oder is wegsmeten worrn.",
        "undo-summary": "Ännern $1 vun [[Special:Contributions/$2|$2]] ([[User talk:$2|Diskuschoon]]) trüchdreiht.",
-       "cantcreateaccounttitle": "Brukerkonto kann nich anleggt warrn",
        "cantcreateaccount-text": "Dat Opstellen vun Brukerkonten vun de IP-Adress '''$1''' ut is vun [[User:$3|$3]] sperrt worrn.\n\nDe Grund weer: ''$2''",
        "viewpagelogs": "Logbook för disse Siet",
        "nohistory": "Disse Siet hett keen Vörgeschicht.",
index 259e6a1..4a97196 100644 (file)
        "passwordreset-emailtext-user": "{{SITENAME}} को $1 प्रयोगकर्ताले  {{SITENAME}} ($4)को लागि खाता विवरणको निम्ति एउटा अनुस्मारकको अनुरोध गरेको छ। निम्न प्रयोगकर्ता {{PLURAL:$3|खाता यस इमेल ठेगानासित सम्बन्धित छ|खाताहरू यस इमेल ठेगानासित सम्बन्धित छन्}}:\n\n$2\n\n{{PLURAL:$3|यो अस्थाई पासवर्डको|यी अस्थाई पासवर्डहरूको}} समय {{PLURAL:$5|एक दिन|$5 दिन}}मा सकिनेछ।\nतपाईंले प्रवेश गरेर अहिले नैं नयाँ पासवर्ड छान्नुहोस्। यदि अरु कसैले अनुरोध गरेको भए अथवा यदि तपाईंलाई मूल पासवर्ड याद भए अनि यसलाई परिवर्तन गर्न चाहनुहुन्न भनें, तपाईंले यस सन्देशलाई अनदेखा गर्नुहोस् र पुरानै पासवर्डलाई चालू राख्नुहोस्।",
        "passwordreset-emailelement": "प्रयोगकर्ताको नाम: \n$1\n\nअस्थाई पासवर्ड: \n$2",
        "passwordreset-emailsentemail": "पासवर्ड परिवर्तनको लागि इमेल पठाइएको छ।",
-       "passwordreset-emailsent-capture": "पासवर्ड परिवर्तनको लागि इमेल पठाइयो, जुन तल देखाइएकोछ।",
-       "passwordreset-emailerror-capture": "पासवर्ड रिसेट इमेल जारि गरिएको छ, जुन तल देखाइएको छ, तर यसलाई {{GENDER:$2|प्रयोगकर्ता}}मा पठाउन विफल भयो: $1",
        "changeemail": "इमेल ठेगाना परिवर्तन गर्नुहोस",
        "changeemail-header": "खाताको इमेल ठेगाना परिवर्तन गर्नुहोस",
        "changeemail-no-info": "यस पृष्ठमा सिधै जानको लागि प्रवेश गर्नु पर्ने हुन्छ ।",
        "undo-nochange": "सम्पादन पहिला नै विफल गरिएको छ ।",
        "undo-summary": "  $1द्वारा पुनरावलोकन [[Special:Contributions/$2|$2]] ([[User talk:$2|वार्तालाप]]) खारेज गर्नुहोस",
        "undo-summary-username-hidden": "अदृश्य प्रयोगकर्ताको संशोधन $1 लाई पहिला जस्तै बनाउने",
-       "cantcreateaccounttitle": "खाता बनाउन सकिएन",
        "cantcreateaccount-text": "IP ठेगाना ('''$1''')बाट खाता खोल्न  [[User:$3|$3]]द्वारा बन्देज लगाइएको छ।\n\n $3ले दिनुभएको कारण  ''$2'' हो",
        "cantcreateaccount-range-text": "<strong>$1</strong> को श्रेणीमा आउने आइपि ठेगानाबाट, जसमा तपाईंको आइपि ठेगाना (<strong>$4</strong>) सामेल छ, नयाँ खाता सृजना [[User:$3|$3]]द्वारा अवरोधित गरिएको छ। \n\n$3 द्वारा दिइएको कारण: \"$2\"",
        "viewpagelogs": "यस पृष्ठका लगहरू हेर्नुहोस्",
        "contributions": "{{GENDER:$1|प्रयोगकर्ता}}का योगदानहरू",
        "contributions-title": "$1को प्रयोगकर्ता योगदानहरू",
        "mycontris": "योगदानहरू",
+       "anoncontribs": "योगदानहरू",
        "contribsub2": " {{GENDER:$3|$1}} ($2)को लागि",
        "contributions-userdoesnotexist": "प्रयोगकर्ता \"$1\" दर्ता गरिएको छैन् ।",
        "nocontribs": "यस मापदण्ड अनुसार परिवर्त पाइएन।",
        "tooltip-t-recentchangeslinked": "यस पृष्ठमा जोडिएका पृष्ठहरूमा हालैको परिवर्तन",
        "tooltip-feed-rss": "यो पृष्ठको लागि RSS फिड",
        "tooltip-feed-atom": "यो पृष्ठको लागि एटम फिड",
-       "tooltip-t-contributions": "यस प्रयोगकर्ताका योगदानहरूको सूची हेर्नुहोस्",
+       "tooltip-t-contributions": "{{GENDER:$1|यस प्रयोगकर्ता}}का योगदानहरूको सूची हेर्नुहोस्",
        "tooltip-t-emailuser": "यो प्रयोगकर्तालाई इमेल पठाउनुहोस्",
        "tooltip-t-info": "यस पृष्ठको बारेमा थप जानकारी",
        "tooltip-t-upload": "फाइल अपलोड गर्ने",
index 3357ad2..4a0ba41 100644 (file)
        "passwordreset-emailelement": "Gebruikersnaam: \n$1\n\nTijdelijk wachtwoord: \n$2",
        "passwordreset-emailsentemail": "Als dit e-mailadres aan uw account gekoppeld is, dan wordt er een e-mail verzonden om uw wachtwoord opnieuw in te stellen.",
        "passwordreset-emailsentusername": "Als er een e-mailadres geregistreerd is voor die gebruikersnaam, dan wordt er een e-mail verzonden om uw wachtwoord opnieuw in te stellen.",
-       "passwordreset-emailsent-capture": "Er is een e-mail voor het opnieuw instellen van een wachtwoord verzonden. Deze wordt hieronder weergegeven.",
-       "passwordreset-emailerror-capture": "Er is een e-mail voor het opnieuw instellen van een wachtwoord aangemaakt. Deze wordt hieronder weergegeven. Het verzenden naar de {{GENDER:$2|gebruiker}} is mislukt om de volgende reden: $1",
        "passwordreset-invalideamil": "Ongeldig e-mailadres",
        "changeemail": "E-mailadres wijzigen of verwijderen",
        "changeemail-header": "Vul dit formulier in om uw e-mailadres te wijzigen. Als u het e-mailadres wilt ontkoppelen van uw account, laat het e-mailadres dan leeg als u het formulier opslaat.",
-       "changeemail-passwordrequired": "U  moet uw wachtwoord invoeren om deze wijziging te bevestigen.",
        "changeemail-no-info": "U moet aangemeld zijn om rechtstreeks toegang te hebben tot deze pagina.",
        "changeemail-oldemail": "Huidig e-mailadres:",
        "changeemail-newemail": "Nieuw e-mailadres:",
        "undo-nochange": "De bewerking lijkt al ongedaan gemaakt te zijn.",
        "undo-summary": "Versie $1 van [[Special:Contributions/$2|$2]] ([[User talk:$2|overleg]]) ongedaan gemaakt",
        "undo-summary-username-hidden": "Versie $1 door een verborgen gebruiker ongedaan gemaakt",
-       "cantcreateaccounttitle": "Registreren is mislukt.",
        "cantcreateaccount-text": "Registreren vanaf dit IP-adres ('''$1''') is geblokkeerd door [[User:$3|$3]].\n\nDe door $3 opgegeven reden is ''$2''",
        "cantcreateaccount-range-text": "Het aanmaken van gebruikers vanaf IP-adressen in de range <strong>$1</strong> is niet mogelijk doordat dit is ingesteld door [[User:$3|$3]]. Uw IP-adres $4 bevindt zich in deze range.\n\nDe reden voor de blokkade is <em>$2</em>",
        "viewpagelogs": "Logboek voor deze pagina bekijken",
index 2e7b628..bffd6e9 100644 (file)
        "passwordreset-emailtext-user": "Brukaren $1 på {{SITENAME}} bad om ei påminning for kontodetaljane dine for {{SITENAME}} ($4). {{PLURAL:$3|Den fylgjande brukarkontoen|Dei fylgjande brukarkontoane}} er assosierte med denne e-postadressa:\n\n$2\n\n{{PLURAL:$3|Dette mellombels passordet|Desse mellombels passorda}} vil verta ugilde om {{PLURAL:$5|éin dag|$5 dagar}}.\nDu bør logga inn og velja eit nytt passord no. Om nokon andre enn deg bad om denne påminninga, eller du har kome i hug det opphavlege passordet og ikkje lenger ynskjer å endra det, kan du sjå bort frå denne meldinga og halda fram med å nytta det gamle passordet ditt.",
        "passwordreset-emailelement": "↓Brukarnamn: \n$1\n\nMellombels passord: \n$2",
        "passwordreset-emailsentemail": "Ein e-post for attendestilling av passord er vorten send",
-       "passwordreset-emailsent-capture": "Ein e-post om attendestilling av passord - vist under - er vorten send",
-       "passwordreset-emailerror-capture": "Ein e-post om attendestilling av passord vart oppretta, og er vist nedanfor; men det lukkast ikkje å senda han til {{GENDER:$2|brukaren}}: $1",
        "changeemail": "↓Endre e-postadresse",
        "changeemail-header": "↓Endre kontoen si e-postadresse",
        "changeemail-no-info": "↓Du må vera pålogga for å få tilgang direkte til denne sida.",
        "undo-failure": "Endringa kunne ikkje attenderullast grunna konflikt med endringar som er gjorde i mellomtida.",
        "undo-norev": "Endringa kunne ikkje fjernast fordi han ikkje finst eller vart sletta",
        "undo-summary": "Rullar attende versjon $1 av [[Special:Contributions/$2|$2]] ([[User talk:$2|diskusjon]])",
-       "cantcreateaccounttitle": "Kan ikkje opprette brukarkonto",
        "cantcreateaccount-text": "Kontooppretting frå denne IP-adressa ('''$1''') er blokkert av [[User:$3|$3]].\n\nGrunnen som vart gjeven av $3 er ''$2''",
        "viewpagelogs": "Vis loggane for sida",
        "nohistory": "Det finst ikkje nokon historikk for denne sida.",
index 66bf6a4..829bb0e 100644 (file)
        "passwordreset-emailtext-user": "{{SITENAME}} 'ਤੇ User $1 ਨੇ ਤੁਹਾਡੇ {{SITENAME}} ($4) ਉਤਲੇ ਪਛਾਣ-ਸ਼ਬਦ ਨੂੰ ਮੁੜ-ਬਣਾਉਣ ਦੀ ਬੇਨਤੀ ਕੀਤੀ ਹੈ। ਇਸ ਈਮੇਲ ਪਤੇ ਨਾਲ਼ ਹੇਠ ਲਿਖੇ {{PLURAL:$3|ਖਾਤੇ|ਖਾਤਿਆਂ}} ਦਾ ਵਾਸਤਾ ਹੈ:\n\n$2\n\n{{PLURAL:$3|ਇਸ ਆਰਜ਼ੀ ਪਛਾਣ-ਸ਼ਬਦ|ਇਹਨਾਂ ਆਰਜ਼ੀ ਪਛਾਣ-ਸ਼ਬਦਾਂ}} ਦੀ ਮਿਆਦ {{PLURAL:$5|ਇੱਕ ਦਿਨ|$5 ਦਿਨਾਂ}} 'ਚ ਮੁੱਕ ਜਾਵੇਗੀ।\nਤੁਹਾਨੂੰ ਹੁਣੇ ਦਾਖ਼ਲ ਹੋ ਕੇ ਕੋਈ ਨਵਾਂ ਪਛਾਣ-ਸ਼ਬਦ ਬਣਾ ਲੈਣਾ ਚਾਹੀਦਾ ਹੈ। ਜੇਕਰ ਕਿਸੇ ਹੋਰ ਨੇ ਇਹ ਬੇਨਤੀ ਕੀਤੀ ਹੈ ਜਾਂ ਤੁਹਾਨੂੰ ਆਪਣਾ ਪਹਿਲਾ ਪਛਾਣ-ਸ਼ਬਦ ਯਾਦ ਆ ਗਿਆ ਹੈ ਅਤੇ ਹੁਣ ਤੁਸੀਂ ਉਹਨੂੰ ਬਦਲ਼ਨਾ ਨਹੀਂ ਲੋਚਦੇ ਤਾਂ ਤੁਸੀਂ ਇਸ ਸੁਨੇਹੇ ਨੂੰ ਅਣਡਿੱਠਾ ਕਰ ਕੇ ਆਪਣਾ ਪੁਰਾਣਾ ਪਛਾਣ-ਸ਼ਬਦ ਵਰਤਦੇ ਰਹਿ ਸਕਦੇ ਹੋ।",
        "passwordreset-emailelement": "ਯੂਜ਼ਰ-ਨਾਂ: \n$1\n\nਆਰਜ਼ੀ ਪਾਸਵਰਡ: \n$2",
        "passwordreset-emailsentemail": "ਇੱਕ ਪਾਸਵਰਡ ਮੁੜ-ਸੈੱਟ ਈ-ਮੇਲ ਭੇਜੀ ਜਾ ਚੁੱਕੀ ਹੈ।",
-       "passwordreset-emailsent-capture": "ਇੱਕ ਯਾਦ-ਦਹਾਨੀ ਈ-ਮੇਲ, ਜਿਹੜੀ ਕਿ ਹੇਠਾਂ ਦਿੱਸ ਰਹੀ ਹੈ, ਭੇਜੀ ਜਾ ਚੁੱਕੀ ਹੈ।",
-       "passwordreset-emailerror-capture": "ਪਛਾਣ-ਸ਼ਬਦ ਮੁੜ ਬਣਾਉਣ ਵਾਸਤੇ ਈਮੇਲ ਤਿਆਰ ਹੋ ਗਈ ਸੀ, ਜੋ ਹੇਠਾਂ ਵਿਖਾਈ ਗਈ ਹੈ, ਪਰ ਇਹਨੂੰ {{GENDER:$2|ਵਰਤੋਂਕਾਰ}} ਵੱਲ ਨਹੀਂ ਘੱਲਿਆ ਜਾ ਸਕਿਆ: $1",
        "passwordreset-invalideamil": "ਗ਼ਲਤ ਈਮੇਲ ਪਤਾ",
        "changeemail": "ਈ-ਮੇਲ ਸਿਰਨਾਵਾਂ ਬਦਲੋ ਜਾੰ ਹਟਾਓ",
        "changeemail-header": "ਖਾਤੇ ਵਾਲਾ ਈ-ਮੇਲ ਸਿਰਨਾਵਾਂ ਬਦਲੋ",
        "undo-nochange": "ਲਗਦਾ ਹੈ ਕਿ ਿਹ ਸੋਧ ਪਹਿਲਾਂ ਹੀ ਮੋੜ ਦਿੱਤੀ ਗਈ ਹੈ।",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|ਗੱਲ-ਬਾਤ]]) ਦੀ ਸੋਧ $1 ਨਕਾਰੀ",
        "undo-summary-username-hidden": "ਗੁਪਤ ਵਰਤੋਂਕਾਰ ਵੱਲੋਂ ਕੀਤੀ $1 ਸੋਧ ਰੱਦ ਕਰੋ",
-       "cantcreateaccounttitle": "ਖਾਤਾ ਬਣਾਇਆ ਨਹੀਂ ਜਾ ਸਕਦਾ",
        "cantcreateaccount-text": "[[User:$3|$3]] ਨੇ ਇਸ IP ਪਤੇ ('''$1''') ਤੋਂ ਖਾਤਾ ਬਣਾਉਣ ਤੇ ਪਾਬੰਦੀ ਲਾਈ ਹੈ।\n\n$3 ਨੇ ਕਾਰਨ ਇਹ ਦੱਸਿਆ ਹੈ, ''$2''",
        "viewpagelogs": "ਇਹ ਸਫ਼ੇ ਲਈ ਇੰਦਰਾਜ ਵੇਖੋ",
        "nohistory": "ਇਸ ਸਫ਼ੇ ਲਈ ਕੋਈ ਸੋਧ ਅਤੀਤ ਨਹੀਂ ਹੈ।",
index 2e10b6a..f6b9259 100644 (file)
        "passwordreset-emailelement": "Nazwa użytkownika: \n$1\n\nTymczasowe hasło: \n$2",
        "passwordreset-emailsentemail": "Jeśli ten adres e‐mail jest przypisany do Twojego konta, zostanie na niego wysłany e-mail do odzyskiwania hasła.",
        "passwordreset-emailsentusername": "Jeśli z tym kontem powiązany jest adres e‐mail, zostanie na niego wysłany e-mail do odzyskiwania hasła.",
-       "passwordreset-emailsent-capture": "Wyświetlony poniżej e‐mail pozwalający na zresetowanie hasła został wysłany.",
-       "passwordreset-emailerror-capture": "Poniżej wyświetlony e‐mail pozwalający na zresetowanie hasła został wygenerowany, ale nie udało się wysłać go do {{GENDER:$2|użytkownika|użytkowniczki}}: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|Został wysłany e-mail|Zostały wysłane e-mail}} z informacjami o resetowaniu hasła. {{PLURAL:$1|Użytkownik i hasło jest pokazany|Lista użytkowników i haseł jest pokazana}} poniżej.",
        "passwordreset-emailerror-capture2": "Wysyłanie e-maila do {{GENDER:$2|użytkownika|użytkowniczki}} nie powiodło się: $1 {{PLURAL:$3|Użytkownik i hasło jest pokazany|Lista użytkowników i haseł jest pokazana}} poniżej.",
        "passwordreset-nocaller": "Musi być podany wywołujący",
        "passwordreset-nodata": "Nie podano ani nazwy użytkownika, ani adresu e-mail",
        "changeemail": "Zmiana lub usunięcie adresu e‐mail",
        "changeemail-header": "Wypełnij ten formularz, aby zmienić swój adres e-mail. Jeśli chcesz usunąć swój adres e-mail, to przy wypełnianiu formularza pozostaw puste pole nowego adresu e-mail.",
-       "changeemail-passwordrequired": "Musisz podać swoje hasło, aby potwierdzić tę zmianę.",
        "changeemail-no-info": "Musisz być zalogowany, by uzyskać bezpośredni dostęp do tej strony.",
        "changeemail-oldemail": "Obecny adres e‐mail:",
        "changeemail-newemail": "Nowy adres e-mail:",
        "undo-nochange": "Wygląda na to, że edycja została już anulowana.",
        "undo-summary": "Anulowanie wersji $1 autora [[Special:Contributions/$2|$2]] ([[User talk:$2|dyskusja]])",
        "undo-summary-username-hidden": "Anulowanie wersji $1 autorstwa ukrytego użytkownika",
-       "cantcreateaccounttitle": "Nie można utworzyć konta",
        "cantcreateaccount-text": "Tworzenie konta z tego adresu IP ('''$1''') zostało zablokowane przez [[User:$3|$3]].\n\nPodany przez $3 powód to ''$2''",
        "cantcreateaccount-range-text": "Tworzenie konta z adresów IP w zakresie <strong>$1</strong>, zawierającego twój adres IP (<strong>$4</strong>), zostało zablokowane przez [[User:$3|$3]].\n\nPodany przez $3 powód to <em>$2</em>",
        "viewpagelogs": "Zobacz rejestry operacji dla tej strony",
index 3ae5be0..e0b4667 100644 (file)
        "passwordreset-emailtext-user": "L'utent $1 ansima a {{SITENAME}} a l'ha ciamà na riampostassion ëd soa ciav për {{SITENAME}} ($4). {{PLURAL:$3|Ël cont utent sì-sota a l'é|Ij cont utent sì-sota a son}} associà a st'adrëssa ëd pòsta eletrònica:\n\n$2\n\n{{PLURAL:$3|Costa ciav provisòria|Coste ciav provisòrie}} a scadran da-sì {{PLURAL:$5|un di|$5 di}}.\nA dovrìa intré ant ël sistema e serne na ciav neuva adess. Se quaidun d'àutr a l'ha fàit costa arcesta, o s'a l'é arcordasse soa ciav original, e a veul pa pi cangela, a peul ignoré ës mëssagi e continué a dovré soa veja ciav.",
        "passwordreset-emailelement": "Stranòm: \n$1\n\nCiav provisòria: \n$2",
        "passwordreset-emailsentemail": "Un mëssagi ëd riampostassion ëd la ciav a l'é stàit spedì.",
-       "passwordreset-emailsent-capture": "Un mëssagi ëd riampostassion ëd la ciav a l'é stàit mandà, e a l'é mostrà sì-sota.",
-       "passwordreset-emailerror-capture": "Un mëssagi ëd riampostassion ëd la ciav a l'é stàit generà, e a l'é smonù sì-sota, ma la spedission a {{GENDER:$2|l'utent}} a l'é falìa: $1",
        "changeemail": "Cangé l'adrëssa ëd pòsta eletrònica",
        "changeemail-header": "Cangé l'adrëssa ëd pòsta eletrònica dël cont",
        "changeemail-no-info": "A dev esse intrà ant ël sistema për andé diretament a costa pàgina.",
        "undo-nochange": "A smija che la modìfica a sia già stàita anulà.",
        "undo-summary": "Gavà la revision $1 fàita da [[Special:Contributions/$2|$2]] ([[User talk:$2|Ciaciarade]])",
        "undo-summary-username-hidden": "Anulé la revision $1 ëd n'utent ëstërmà",
-       "cantcreateaccounttitle": "As peul pa registresse d'utent",
        "cantcreateaccount-text": "La cression ëd cont neuv a parte da st'adrëssa IP-sì ('''$1''') a l'é stàita blocà da [[User:$3|$3]].\n\nLa rason butà da $3 për ël blocagi a l'é stàita: ''$2''",
        "cantcreateaccount-range-text": "La creassion ëd cont da l'adrëssa IP ant l'antërval <strong>$1</strong>, ch'a comprend soa adrëssa IP (<strong>$4</strong>), a l'é stàita blocà da [[User:$3|$3]].\n\nLa rason dàita da $3 a l'é <em>$2</em>",
        "viewpagelogs": "Smon ij registr dë sta pàgina-sì",
index a7709b6..a4514e7 100644 (file)
        "passwordreset-emailelement": "Usuário: \n$1\n\nSenha temporária: \n$2",
        "passwordreset-emailsentemail": "Se este é um endereço de e-mail registrado para a sua conta, em seguida, um e-mail de redefinição de senha será enviada.",
        "passwordreset-emailsentusername": "Se houver um endereço de email associado a esta conta, ser-lhe-á enviada uma mensagem para redefinir a sua senha.",
-       "passwordreset-emailsent-capture": "Foi enviado um e-mail de lembrete, que é mostrado abaixo.",
-       "passwordreset-emailerror-capture": "Foi gerado um e-mail de recuperação da senha, conforme mostrado abaixo, mas o envio {{GENDER:$2|ao usuário|à usuária}} falhou. $1",
        "passwordreset-emailsent-capture2": "A redefinição da senha {{PLURAL:$1|do e-mail|dos e-mails}} foi enviada. {{PLURAL:$1|O nome de usuário e senha|A lista de nomes de usuário e senhas}} encontram-se a seguir.",
        "changeemail": "Alterar ou remover endereço de email",
        "changeemail-header": "Preencha este formulário para alterar seu endereço de e-mail. Se você gostaria de remover a associação de qualquer endereço de e-mail da sua conta, deixe o novo endereço de email em branco quando enviar o formulário.",
-       "changeemail-passwordrequired": "Você terá que digitar sua senha para confirmar esta mudança.",
        "changeemail-no-info": "Para acessar diretamente esta página você tem de estar autenticado.",
        "changeemail-oldemail": "Endereço de e-mail atual:",
        "changeemail-newemail": "Novo endereço de e-mail:",
        "content-model-css": "CSS",
        "content-json-empty-object": "Objeto vazio",
        "content-json-empty-array": "Array vazia",
+       "deprecated-self-close-category": "Páginas com etiquetas HTML de autofechamento não válidas",
        "duplicate-args-warning": "<strong> Aviso: </strong> [[:$1]] está chamando [[:$2]] com mais de um valor para o parâmetro \"$3\". Será utilizado apenas o último valor fornecido.",
        "duplicate-args-category": "Páginas com argumentos de predefinições duplicados",
        "duplicate-args-category-desc": "A pagina contem modelos que usam argumentos duplicados, como <code><nowiki>{{foo|bar=1|bar=2}}</nowiki></code> ou <code><nowiki>{{foo|bar|1=baz}}</nowiki></code>.",
        "undo-nochange": "Parece que a edição já foi desfeita.",
        "undo-summary": "Desfeita a edição $1 de [[Special:Contributions/$2|$2]] ([[User talk:$2|Discussão]])",
        "undo-summary-username-hidden": "Desfazer a revisão $1 de um usuário oculto",
-       "cantcreateaccounttitle": "Não é possível criar uma conta",
        "cantcreateaccount-text": "Este IP ('''$1''') foi bloqueado de criar novas contas por [[User:$3|$3]].\n\nA justificativa apresentada por $3 foi ''$2''",
        "cantcreateaccount-range-text": "A criação de conta a partir dos endereços IP no intervalo <strong>$1</strong>, que inclui o seu endereço IP (<strong>$4</strong>), foi bloqueada por [[User:$3|$3]].\n\nA razão dada por $3 é <em>$2</em>",
        "viewpagelogs": "Ver registros para esta página",
index 3a0cfb0..85894af 100644 (file)
        "passwordreset-emailelement": "{{GENDER:$1|Utilizador|Utilizadora}}: \n$1\n\nPalavra-passe temporária: \n$2",
        "passwordreset-emailsentemail": "Se este é o endereço de correio eletrónico associado a esta conta, ser-lhe-á enviada uma palavra-passe de reposição.",
        "passwordreset-emailsentusername": "Se houver um endereço de correio eletrónico associado a esta conta, ser-lhe-á enviada uma mensagem para redefinir a sua palavra-passe.",
-       "passwordreset-emailsent-capture": "Foi enviado um correio eletrónico para recuperação da palavra-passe, que é mostrado abaixo.",
-       "passwordreset-emailerror-capture": "Foi gerado um correio eletrónico para redefinição da palavra-passe, mostrado abaixo, mas o seu envio para {{GENDER:$2|o utilizador|a utilizadora}} falhou: $1",
        "passwordreset-invalideamil": "Correio eletrónico inválido",
        "passwordreset-nodata": "Não foram fornecidos nome de utilizador(a) nem endereço de correio eletrónico",
        "changeemail": "Alterar ou remover o endereço de correio eletrónico",
        "changeemail-header": "Complete este formulário para alterar o seu endereço de correio eletrónico. Se quer eliminar a associação de qualquer endereço de correio eletrónico com a sua conta, deixe em branco o novo endereço de correio eletrónico ao submeter o formulário.",
-       "changeemail-passwordrequired": "Necessita de introduzir a sua palavra-passe para confirmar esta alteração.",
        "changeemail-no-info": "Precisa de iniciar sessão para aceder diretamente a esta página.",
        "changeemail-oldemail": "Correio eletrónico atual:",
        "changeemail-newemail": "Novo endereço de correio eletrónico:",
        "content-model-css": "CSS",
        "content-json-empty-object": "Objeto vazio",
        "content-json-empty-array": "Matriz vazia",
+       "deprecated-self-close-category": "Páginas com etiquetas HTML de autofechamento não válidas",
        "duplicate-args-warning": "<strong>Aviso:</strong> [[:$1]] chama [[:$2]] com mais de um valor para o parâmetro \"$3\". Somente o último valor fornecido será utilizado.",
        "duplicate-args-category": "Páginas com argumentos de predefinições duplicados",
        "duplicate-args-category-desc": "A página contém campos de predefinições que utilizam duplicatas de argumentos, tais como <code><nowiki>{{foo|bar=1|bar=2}}</nowiki></code> ou <code><nowiki>{{foo|bar|1=baz}}</nowiki></code>.",
        "undo-nochange": "A edição parece já ter sido desfeita.",
        "undo-summary": "Desfez a edição $1 de [[Special:Contributions/$2|$2]] ([[User talk:$2|Discussão]])",
        "undo-summary-username-hidden": "Desfez a edição $1 de um utilizador oculto",
-       "cantcreateaccounttitle": "Não é possível criar uma conta",
        "cantcreateaccount-text": "A criação de contas a partir deste endereço IP ('''$1''') foi bloqueada por [[User:$3|$3]].\n\nO motivo apresentado por $3 foi ''$2''",
        "cantcreateaccount-range-text": "A criação de conta a partir dos endereços IP no intervalo <strong>$1</strong>, que inclui o seu endereço IP (<strong>$4</strong>), foi bloqueada por [[User:$3|$3]].\n\nA razão dada por $3 é <em>$2</em>",
        "viewpagelogs": "Ver registos para esta página",
        "showhideselectedversions": "Mostrar/ocultar versões selecionadas",
        "editundo": "desfazer",
        "diff-empty": "(Sem diferenças)",
-       "diff-multi-sameuser": "(Há {{PLURAL:$1|uma edição intermédia|$1 edições intermédias}} do mesmo utilizador que não estão a ser apresentadas)",
+       "diff-multi-sameuser": "(Há {{PLURAL:$1|uma edição intermédia do mesmo utilizador que não está a ser apresentada|$1 edições intermédias do mesmo utilizador que não estão a ser apresentadas}})",
        "diff-multi-otherusers": "(Há {{PLURAL:$1|uma revisão intermédia|$1 revisões intermédias}} de {{PLURAL:$2|outro utilizador|$2 utilizadores}} que não {{PLURAL:$1|está a ser apresentada|estão a ser apresentadas}})",
        "diff-multi-manyusers": "({{PLURAL:$1|Uma edição intermédia|$1 edições intermédias}} de mais de {{PLURAL:$2|um utilizador|$2 utilizadores}} não {{PLURAL:$1|apresentada|apresentadas}})",
        "difference-missing-revision": "{{PLURAL:$2|Uma revisão|$2 revisões}} desta diferença ($1) não {{PLURAL:$2|foi encontrada|foram encontradas}}.\n\nIsto é geralmente causado por seguir uma ligação de histórico desatualizada para uma página que foi eliminada.\nOs detalhes podem ser encontrados no [{{fullurl:{{#Special:Log}}/delete|page={{FULLPAGENAMEE}}}} registo de eliminação].",
        "undeletedrevisions": "$1 {{PLURAL:$1|edição restaurada|edições restauradas}}",
        "undeletedrevisions-files": "$1 {{PLURAL:$1|edição restaurada|edições restauradas}} e $2 {{PLURAL:$2|ficheiro restaurado|ficheiros restaurados}}",
        "undeletedfiles": "{{PLURAL:$1|ficheiro restaurado|$1 ficheiros restaurados}}",
-       "cannotundelete": "Restauração falhada:\n$1",
+       "cannotundelete": "Algumas ou todas as restaurações falharam:\n$1",
        "undeletedpage": "'''$1 foi restaurada'''\n\nConsulte o [[Special:Log/delete|registo de eliminações]] para um registo das eliminações e restaurações mais recentes.",
        "undelete-header": "Consulte o [[Special:Log/delete|registo de eliminações]] para ver as páginas eliminadas recentemente.",
        "undelete-search-title": "Pesquisar páginas eliminadas",
        "sp-contributions-newbies-sub": "Para contas novas",
        "sp-contributions-newbies-title": "Contribuições de contas novas",
        "sp-contributions-blocklog": "registo de bloqueios",
-       "sp-contributions-suppresslog": "contribuições suprimidas",
-       "sp-contributions-deleted": "contribuições eliminadas",
+       "sp-contributions-suppresslog": "contribuições de {{GENDER:$1|utilizador|utilizadora|utilizador(a)}} suprimidas",
+       "sp-contributions-deleted": "contribuições de {{GENDER:$1|utilizador|utilizadora|utilizador(a)}} eliminadas",
        "sp-contributions-uploads": "carregamentos",
        "sp-contributions-logs": "registos",
        "sp-contributions-talk": "discussão",
index 261ca25..998511d 100644 (file)
                        "Guycn2",
                        "2axterix2",
                        "Ата",
-                       "Matěj Suchánek"
+                       "Matěj Suchánek",
+                       "Chaduvari"
                ]
        },
        "sidebar": "{{notranslate}}",
        "passwordreset-emailelement": "This is a body of a password reset email to allow them into the system with a new password. Parameters:\n* $1 - the user's login name. This parameter can be used for GENDER.\n* $2 - the temporary password given by the system",
        "passwordreset-emailsentemail": "Used in [[Special:PasswordReset]].\n\nSee also:\n* {{msg-mw|Passwordreset-emailsent-capture}}\n* {{msg-mw|Passwordreset-emailerror-capture}}",
        "passwordreset-emailsentusername": "Used in [[Special:PasswordReset]].\n\nSee also:\n* {{msg-mw|Passwordreset-emailsent-capture}}\n* {{msg-mw|Passwordreset-emailerror-capture}}",
-       "passwordreset-emailsent-capture": "Used in [[Special:PasswordReset]].\n\nSee also:\n* {{msg-mw|Passwordreset-emailsentemail}}\n* {{msg-mw|Passwordreset-emailsentusername}}\n* {{msg-mw|Passwordreset-emailerror-capture}}",
-       "passwordreset-emailerror-capture": "Error message displayed in [[Special:PasswordReset]] when sending an email fails. Parameters:\n* $1 - error message\n* $2 - username, used for GENDER\nSee also:\n* {{msg-mw|Passwordreset-emailsentemail}}\n* {{msg-mw|Passwordreset-emailsentusername}}\n* {{msg-mw|Passwordreset-emailsent-capture}}",
        "passwordreset-emailsent-capture2": "Used in [[Special:PasswordReset]].\n\nParameters:\n* $1 - number of accounts notified\n\nSee also:\n* {{msg-mw|Passwordreset-emailsentemail}}\n* {{msg-mw|Passwordreset-emailsentusername}}\n* {{msg-mw|Passwordreset-emailerror-capture}}",
        "passwordreset-emailerror-capture2": "Error message displayed in [[Special:PasswordReset]] when sending an email fails. Parameters:\n* $1 - error message\n* $2 - username, used for GENDER\n* $3 - number of accounts notified\n\nSee also:\n* {{msg-mw|Passwordreset-emailsentemail}}\n* {{msg-mw|Passwordreset-emailsentusername}}\n* {{msg-mw|Passwordreset-emailsent-capture}}\n* {{msg-mw|Passwordreset-emailerror-capture}}",
        "passwordreset-nocaller": "Shown when a password reset was requested but the caller was not provided. This is an internal error.",
        "changeemail": "Title of [[Special:ChangeEmail|special page]]. This page also allows removing the user's email address.",
        "changeemail-summary": "{{ignored}}",
        "changeemail-header": "Text of [[Special:ChangeEmail]].",
-       "changeemail-passwordrequired": "Shown on [[Special:ChangeEmail]] if users are required to enter their password to change their email address..",
        "changeemail-no-info": "Error message for [[Special:ChangeEmail]].\n\nParameters:\n* $1 (unused) - a link to [[Special:UserLogin]] with {{msg-mw|loginreqlink}} as link description",
        "changeemail-oldemail": "Label for e-mail address field in [[Special:ChangeEmail]].",
        "changeemail-newemail": "Label for e-mail address field in [[Special:ChangeEmail]]. See also {{msg-mw|changeemail-newemail-help}}",
        "undo-nochange": "Message appears if an attempt to revert an edit by clicking the \"undo\" link results in an edit making no change to the current version of the page.\n\nSee also:\n* {{msg-mw|Undo-failure}}\n* {{msg-mw|Undo-norev}}",
        "undo-summary": "Edit summary for an undo action. Parameters:\n* $1 - revision ID\n* $2 - username\n{{Identical|Undo}}",
        "undo-summary-username-hidden": "Edit summary for an undo action where the username of the old revision is hidden.\n\nParameters:\n* $1 - the revision ID being undone\nSee also:\n* {{msg-mw|Undo-summary}}",
-       "cantcreateaccounttitle": "Used as title of the error message {{msg-mw|Cantcreateaccount-text}}.",
-       "cantcreateaccount-text": "Used as error message, with the title {{msg-mw|Cantcreateaccounttitle}}.\n* $1 - target IP address\n* $2 - reason or {{msg-mw|Blockednoreason}}\n* $3 - username\nSee also:\n* {{msg-mw|Cantcreateaccount-range-text}}",
+       "cantcreateaccount-text": "Used as error message when account creation is prevented by an IP block.\n* $1 - target IP address\n* $2 - reason or {{msg-mw|Blockednoreason}}\n* $3 - username\nSee also:\n* {{msg-mw|Cantcreateaccount-range-text}}",
        "cantcreateaccount-range-text": "Used instead of the {{msg-mw|Cantcreateaccount-text}} when the block is a range block.\n* $1 - target IP address range\n* $2 - reason or {{msg-mw|Blockednoreason}}\n* $3 - username\n* $4 - current user's IP address",
        "createaccount-hook-aborted": "Placeholder message to return with API errors on account create; passes through the message from a hook {{notranslate}}",
        "viewpagelogs": "Link displayed in history of pages",
        "uploadstash-errclear": "Used as error message in [[Special:UploadStash]].",
        "uploadstash-refresh": "Used as link text in [[Special:UploadStash]].",
        "uploadstash-thumbnail": "Used as link text in [[Special:UploadStash]].",
+       "uploadstash-exception": "Error message shown when an action related to the upload stash fails unexpectedly.\n\nParameters:\n* $1 - exception name, e.g. 'UploadStashFileNotFoundException'\n* $2 - exceptions details (always in English), e.g. 'cannot find path, or not a plain file'",
        "invalid-chunk-offset": "Error that can happen if chunks get uploaded out of order.\nAs a result of this error, clients can continue from an offset provided or restart the upload.\nUsed on [[Special:UploadWizard]].",
        "img-auth-accessdenied": "[[mw:Manual:Image Authorization|Manual:Image Authorization]]: Access Denied\n{{Identical|Access denied}}",
        "img-auth-nopathinfo": "[[mw:Manual:Image Authorization|Manual:Image Authorization]]: Missing PATH_INFO - see english description\n{{Doc-important|This is plain text. Do not use any wiki syntax.}}",
        "undeletehistorynoadmin": "Used in [[Special:Undelete]].\n\nSee also:\n* {{msg-mw|Undeletehistory}}\n* {{msg-mw|Undeleterevdel}}",
        "undelete-revision": "Shown in \"View and restore deleted pages\" ([[Special:Undelete/$1]]).\nParameters:\n* $1 - deleted page name\n* $2 - (unused)\n* $3 - username (author of revision, not who deleted it)\n* $4 - date of the revision (localized)\n* $5 - time of the revision (localized)\nExample (in English):\n* Deleted revision of [[Main Page]] (as of 14 September 2013, at 08:17) by [[User:Username|Username]]:",
        "undeleterevision-missing": "Used as warning when undeleting the revision.",
+       "undeleterevision-duplicate-revid": "Used as warning when some revisions could not be undeleted due to <code>rev_id</code> collisions.  Parameters:\n* - Number of revisions that could not be restored for this reason.",
        "undelete-nodiff": "Used in [[Special:Undelete]].",
        "undeletebtn": "Shown on [[Special:Undelete]] as button caption and on [[Special:Log/delete|deletion log]] after each entry (for sysops).\n\n{{Identical|Restore}}",
        "undeletelink": "Display name of link to undelete a page used on [[Special:Log/delete]]\n\n{{Identical|View}}\n{{Identical|Restore}}",
        "sp-contributions-newbies-sub": "Note at the top of the page of results for a search on [[Special:Contributions]] where 'Show contributions for new accounts only' has been selected.",
        "sp-contributions-newbies-title": "The page title in your browser bar, but not the page title.\n\nSee also:\n* {{msg-mw|Sp-contributions-newbies-sub}}",
        "sp-contributions-blocklog": "Used as a display name for a link to the block log on for example [[Special:Contributions/Mediawiki default]]\n\nUsed as link title in [[Special:Contributions]] and in [[Special:DeletedContributions]].\n\nSee also:\n* {{msg-mw|Sp-contributions-talk}}\n* {{msg-mw|Change-blocklink}}\n* {{msg-mw|Unblocklink}}\n* {{msg-mw|Blocklink}}\n* {{msg-mw|Sp-contributions-uploads}}\n* {{msg-mw|Sp-contributions-logs}}\n* {{msg-mw|Sp-contributions-deleted}}\n* {{msg-mw|Sp-contributions-userrights}}\n{{Identical|Block log}}",
-       "sp-contributions-suppresslog": "Used as a display name for a link to log entries of suppressed edits made by that user.\n\nUsed as link title in [[Special:Contributions]] and in [[Special:DeletedContributions]].\n\nSee also {{msg-mw|sp-contributions-deleted}}, {{msg-mw|sp-deletedcontributions-contribs}}, {{msg-mw|contributions}}, {{msg-mw|deletedcontributions-title}}.",
-       "sp-contributions-deleted": "This is a link anchor used in [[Special:Contributions]]/''name'', when user viewing the page has the right to delete pages, or to restore deleted pages.\n\nUsed as link title in [[Special:Contributions]].\n\nSee also:\n* {{msg-mw|Sp-contributions-talk}}\n* {{msg-mw|Change-blocklink}}\n* {{msg-mw|Unblocklink}}\n* {{msg-mw|Blocklink}}\n* {{msg-mw|Sp-contributions-blocklog}}\n* {{msg-mw|Sp-contributions-uploads}}\n* {{msg-mw|Sp-contributions-logs}}\n* {{msg-mw|Sp-contributions-userrights}}",
+       "sp-contributions-suppresslog": "Used as a display name for a link to log entries of suppressed edits made by that user.\n\nUsed as link title in [[Special:Contributions]] and in [[Special:DeletedContributions]]. Parameters:\n* $1 is a plain text username used for GENDER.\nSee also {{msg-mw|sp-contributions-deleted}}, {{msg-mw|sp-deletedcontributions-contribs}}, {{msg-mw|contributions}}, {{msg-mw|deletedcontributions-title}}.",
+       "sp-contributions-deleted": "This is a link anchor used in [[Special:Contributions]]/''name'', when user viewing the page has the right to delete pages, or to restore deleted pages.\n\nUsed as link title in [[Special:Contributions]]. Parameters:\n* $1 is a plain text username used for GENDER.\nSee also:\n* {{msg-mw|Sp-contributions-talk}}\n* {{msg-mw|Change-blocklink}}\n* {{msg-mw|Unblocklink}}\n* {{msg-mw|Blocklink}}\n* {{msg-mw|Sp-contributions-blocklog}}\n* {{msg-mw|Sp-contributions-uploads}}\n* {{msg-mw|Sp-contributions-logs}}\n* {{msg-mw|Sp-contributions-userrights}}",
        "sp-contributions-uploads": "Used as link title in [[Special:Contributions]] and in [[Special:DeletedContributions]].\n\nSee also:\n* {{msg-mw|Sp-contributions-talk}}\n* {{msg-mw|Change-blocklink}}\n* {{msg-mw|Unblocklink}}\n* {{msg-mw|Blocklink}}\n* {{msg-mw|Sp-contributions-blocklog}}\n* {{msg-mw|Sp-contributions-logs}}\n* {{msg-mw|Sp-contributions-deleted}}\n* {{msg-mw|Sp-contributions-userrights}}\n{{Identical|Upload}}",
        "sp-contributions-logs": "Appears as an action link in the header of the Special:Contributions/''Username'' pages (e.g. \"For Somebody (talk | block log | logs)\").\n\nUsed as link title in [[Special:Contributions]] and in [[Special:DeletedContributions]].\n\nSee also:\n* {{msg-mw|Sp-contributions-talk}}\n* {{msg-mw|Change-blocklink}}\n* {{msg-mw|Unblocklink}}\n* {{msg-mw|Blocklink}}\n* {{msg-mw|Sp-contributions-blocklog}}\n* {{msg-mw|Sp-contributions-uploads}}\n* {{msg-mw|Sp-contributions-deleted}}\n* {{msg-mw|Sp-contributions-userrights}}\n{{Identical|Log}}",
        "sp-contributions-talk": "This is a link anchor used in the [[Special:Contributions]]/''usernamename'' pages.\nThe link appears in a list of similar ones separated by {{msg-mw|pipe-separator}}, e.g. like this:<br />\n( talk | block log | logs | deleted contributions | rights management )\n\nUsed as link title in [[Special:Contributions]] and in [[Special:DeletedContributions]].\n\nSee also:\n* {{msg-mw|change-blocklink}}\n* {{msg-mw|unblocklink}}\n* {{msg-mw|blocklink}}\n* {{msg-mw|sp-contributions-blocklog}}\n* {{msg-mw|sp-contributions-uploads}}\n* {{msg-mw|sp-contributions-logs}}\n* {{msg-mw|sp-contributions-deleted}}\n* {{msg-mw|sp-contributions-userrights}}\n{{Identical|Talk}}",
        "tags-active-yes": "Table cell contents if given tag is \"active\".\n\nSee also:\n* {{msg-mw|Tags-active-no}}\n{{Identical|Yes}}",
        "tags-active-no": "Table cell contents if given tag is not \"active\".\n\nSee also:\n* {{msg-mw|Tags-active-yes}}\n{{Identical|No}}",
        "tags-source-extension": "Table cell contents if given tag can be applied automatically by a software [[mw:Manual:Extensions|extension]].\n\nSee also:\n* {{msg-mw|Tags-source-manual}}\n* {{msg-mw|Tags-source-none}}",
-       "tags-source-manual": "Table cell contents if given tag can be applied by users or bots.\n\nSee also:\n* {{msg-mw|Tags-source-extension}}\n* {{msg-mw|Tags-source-none}}",
+       "tags-source-manual": "\"Applied\" is not past tense, but an adjective that describes an action that sometimes happens, as in the sentence: \"(this tag is usually) applied by users and bots\".\n\nTable cell contents if given tag can be applied by users or bots.\n\nSee also:\n* {{msg-mw|Tags-source-extension}}\n* {{msg-mw|Tags-source-none}}",
        "tags-source-none": "Table cell contents if given tag is no longer in use. (It was applied in the past, but it is currently not applied.)\n\nSee also:\n* {{msg-mw|Tags-source-extension}}\n* {{msg-mw|Tags-source-manual}}",
        "tags-edit": "Used on [[Special:Tags]]. Verb. Used as display text on a link to create/edit a description.\n{{Identical|Edit}}",
        "tags-delete": "Used on [[Special:Tags]]. Verb. Used as display text on a link to delete a tag.\n{{Identical|Delete}}",
index 080ae69..2dafc36 100644 (file)
@@ -29,7 +29,8 @@
                        "ImGelu",
                        "Wintereu",
                        "Rsocol",
-                       "Nemo bis"
+                       "Nemo bis",
+                       "Turbojet"
                ]
        },
        "tog-underline": "Sublinierea legăturilor:",
        "passwordreset-emailelement": "Nume de utilizator: \n$1\n\nParolă temporară: \n$2",
        "passwordreset-emailsentemail": "Dacă această adresă de e-mail este asociată contului dumneavoastră, atunci se va trimite un e-mail de resetare a parolei.",
        "passwordreset-emailsentusername": "Dacă există o adresă de e-mail asociată acestui nume de utilizator, atunci se va trimite un e-mail de resetare a parolei.",
-       "passwordreset-emailsent-capture": "Un mesaj de resetare a parolei a fost trimis, fiind afișat mai jos.",
-       "passwordreset-emailerror-capture": "Un mesaj de resetare a parolei a fost generat (fiind afișat mai jos), dar trimiterea sa către {{GENDER:$2|utilizator}} a eșuat: $1",
        "passwordreset-invalideamil": "Adresă de e-mail nevalidă",
        "passwordreset-nodata": "Nu au fost furnizate un nume de utilizator sau o adresă de e-mail",
        "changeemail": "Modificare sau înlăturare adresă de e-mail",
        "changeemail-header": "Completați acest formular pentru a vă schimba adresa de e-mail. Dacă doriți să înlăturați orice asociere a unei adrese de e-mail cu contul dumneavoastră, lăsați necompletat câmpul pentru introducerea unei noi adrese de e-mail atunci când trimiteți formularul.",
-       "changeemail-passwordrequired": "Va trebui să introduceți parola pentru a confirma această schimbare.",
        "changeemail-no-info": "Trebuie să fiți autentificat pentru a accesa această pagină direct.",
        "changeemail-oldemail": "Adresa de e-mail actuală:",
        "changeemail-newemail": "Noua adresă de e-mail:",
        "watchthis": "Urmărește această pagină",
        "savearticle": "Salvare pagină",
        "publishpage": "Publică pagina",
+       "publishchanges": "Publică modificările",
        "preview": "Previzualizare",
        "showpreview": "Previzualizare",
        "showdiff": "Afișare diferențe",
        "undo-nochange": "Se pare că această modificare a fost deja anulată.",
        "undo-summary": "Anularea modificării $1 făcute de [[Special:Contributions/$2|$2]] ([[User talk:$2|Discuție]])",
        "undo-summary-username-hidden": "Anularea versiunii $1 a unui utilizator ascuns",
-       "cantcreateaccounttitle": "Crearea contului nu poate fi realizată",
        "cantcreateaccount-text": "Crearea de conturi de la această adresă IP ('''$1''') a fost blocată de [[User:$3|$3]].\n\nMotivul invocat de $3 este ''$2''",
        "cantcreateaccount-range-text": "Crearea de conturi de la adresele IP din gama <strong>$1</strong>, care o include și pe a dumneavoastră (<strong>$4</strong>), a fost blocată de [[User:$3|$3]].\n\nMotivul invocat de $3 este <em>$2</em>",
        "viewpagelogs": "Afișează jurnalele paginii",
index 823d0bb..a9db650 100644 (file)
        "passwordreset-emailtext-user": "L'utende $1 sus a {{SITENAME}} ave richieste 'na mail pe arrecurdarse le dettaglie d'u cunde sue pe {{SITENAME}}\n($4). {{PLURAL:$3|'U cunde utende seguende jè|le cunde utinde seguende sonde}} associate cu st'indirizze e-mail:\n\n$2\n\n{{PLURAL:$3|Sta passuord temboranèe scade|Ste passuord temboranèe scadene}}  'mbrà {{PLURAL:$5|'nu sciurne|$5 sciurne}}.\nTu avissa trasè e scacchià 'na passuord nova. Ce quacchedun'otre ha fatte sta richieste, o ce tu t'è arrecurdate 'a passuord origgenale toje, e non g'a vuè ccu cange cchiù, tu puè ignorà stu messagge e condinuà ausanne 'a passuord vecchie.",
        "passwordreset-emailelement": "Nome utende: \n$1\n\nPassuord temboranèe: \n$2",
        "passwordreset-emailsentemail": "Ce quiste jè 'n'e-mail pu cunde tune, allore 'na password azzerate ha state mannate addà.",
-       "passwordreset-emailsent-capture": "'Na e-mail pe azzeramende d'a passuord ha state mannate, ca jè fatte vedè aqquà sotte.",
-       "passwordreset-emailerror-capture": "'Na e-mail de azzeramende d'a passuord ha state generate, ca jè fatte vedè aqquà sotte, ma 'u 'nvie a {{GENDER:$2|l'utende}} ha fallite: $1",
        "changeemail": "Cange o live 'u 'ndirizze e-mail",
        "changeemail-header": "Comblete stu module pe cangià 'u 'ndirizze email. Ce tu vuè ccu live l'associazione cu ogne indirizze email da 'u cunde tune, lasse 'u 'ndirizze email vacande quanne conferme 'u module.",
        "changeemail-no-info": "Tu a essere collegate pe accedere a sta pàgene direttamende.",
        "undo-nochange": "'U cangiamende pare ca ha state già annullate.",
        "undo-summary": "Repristine 'a revisione $1 da [[Special:Contributions/$2|$2]] ([[User talk:$2|'Ngazzaminde]])",
        "undo-summary-username-hidden": "Annulle 'a revisione $1 da 'n'utende scunnute",
-       "cantcreateaccounttitle": "Non ge puè ccrejà 'nu cunde utende",
        "cantcreateaccount-text": "'A creazione d'u cunde utende da stu 'ndirizze IP ('''$1''') ha state blocchete da [[User:$3|$3]].\n\n'U mutive dete da $3 jè ''$2''",
        "cantcreateaccount-range-text": "'A crejazzione d'u cunde da l'indirizze IP jndr'à l'indervalle \"$1\", 'u quale 'nglude 'u 'ndirizze IP tune (<strong>$4</strong>), ha state bloccate da [[User:$3|$2]].",
        "viewpagelogs": "Vide l'archivie pe sta pàgene",
index a72df46..f7b7c94 100644 (file)
        "passwordreset-emailelement": "Имя участника: \n$1\n\nВременный пароль: \n$2",
        "passwordreset-emailsentemail": "Если это адрес электронной почты связан с вашей учётной записью, вам будет отправлено письмо для сброса пароля.",
        "passwordreset-emailsentusername": "Если есть адрес электронной почты, связанный с этим именем участника, то будет отправлено письмо для восстановления пароля.",
-       "passwordreset-emailsent-capture": "Отправлено электронное письмо с информацией о сбросе пароля, текст которого можно увидеть ниже.",
-       "passwordreset-emailerror-capture": "Было создано электронное письмо с информацией о сбросе пароля, текст которого можно увидеть ниже, однако его не удалось отправить {{GENDER:$2|участнику|участнице}} по следующей причине: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|Письмо|Письма}} для сброса пароля {{PLURAL:$1|было отправлено|были отправлены}}. {{PLURAL:$1|Логин и пароль показаны|Список логинов и паролей показан}} ниже.",
        "passwordreset-emailerror-capture2": "Отправка {{GENDER:$2|участнику}} письма по электронной почте не удалась: $1 В {{PLURAL:$3|логин и пароль показаны|список логинов и паролей показан}} ниже.",
        "passwordreset-nocaller": "Должен быть предоставлен источник вызова",
        "passwordreset-nodata": "Ни имя участника, ни адрес электронной почты не были предоставлены",
        "changeemail": "Изменить или удалить адрес электронной почты",
        "changeemail-header": "Заполните эту форму, чтобы изменить свой адрес электронной почты. Если вы хотите отвязать свой адрес электронной почты от учётной записи, то при заполнении формы оставьте пустым поле нового адреса электронной почты.",
-       "changeemail-passwordrequired": "Чтобы подтвердить это изменение, вам нужно будет ввести свой пароль.",
        "changeemail-no-info": "Чтобы обращаться непосредственно к этой странице, вам следует представиться системе.",
        "changeemail-oldemail": "Текущий адрес электронной почты:",
        "changeemail-newemail": "Новый адрес электронной почты:",
        "watchthis": "Следить за этой страницей",
        "savearticle": "Записать страницу",
        "savechanges": "Сохранить изменения",
-       "publishpage": "издавать страницу",
-       "publishchanges": "Ð\9eпÑ\83бликоваÑ\82Ñ\8c Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¸Ñ\8f",
+       "publishpage": "Создать страницу",
+       "publishchanges": "Ð\97апиÑ\81аÑ\82Ñ\8c Ñ\81Ñ\82Ñ\80аниÑ\86Ñ\83",
        "preview": "Предпросмотр",
        "showpreview": "Предварительный просмотр",
        "showdiff": "Внесённые изменения",
        "undo-nochange": "Правка, похоже, уже была отменена.",
        "undo-summary": "Отмена правки $1, сделанной {{GENDER:$2|участником|участницей}} [[Special:Contribs/$2|$2]] ([[User talk:$2|обс.]])",
        "undo-summary-username-hidden": "Отмена правки $1, сделанной участником, чьё имя скрыто",
-       "cantcreateaccounttitle": "Невозможно создать учётную запись",
        "cantcreateaccount-text": "Создание учётных записей с этого IP-адреса ('''$1''') было заблокировано {{GENDER:$3|участником|участницей|}} [[User:$3|$3]].\n\n$3 {{GENDER:$3|указал|указала}} следующую причину: ''$2''.",
        "cantcreateaccount-range-text": "{{GENDER:$3|Участник|Участница}} [[User:$3|$3]] {{GENDER:$3|установил|установила}} запрет на создание учётных записей из диапазона IP-адресов <strong>$1</strong>, включающего ваш IP-адрес (<strong>$4</strong>). \n\nБыла указана следующая причина: $2.",
        "viewpagelogs": "Показать журналы для этой страницы",
index 39b1992..f4ff3ad 100644 (file)
        "passwordreset-emailtext-user": "$1 सदस्यः {{SITENAME}}($4) जालस्थानस्य  कृते कूटशब्दपरिवर्तनस्य विनतिम् अकरोत् । निम्न{{PLURAL:$3|सदस्यः|सदस्याः}} अनेन वि-पत्रेण सह सल्लग्नः अस्ति/सल्लग्नाः सन्ति ।\n\n$2\n\n{{PLURAL:$3|एषः अल्पकालीनकूटशब्दः|एते अल्पकालीनकूटशब्दाः}} {{PLURAL:$5|चतुर्विंशतिघण्टासु|$5 दिनेषु}} निरस्तः भविष्यति/निरस्ताः भविष्यन्ति ।\nअधुना प्रवेशं सम्प्राप्य कूटशब्दः परिवर्तनीयः एव । \n\nनिम्नकारणानि यदि सन्ति, तर्हि एनं सन्देशम् अवगण्यताम् ।\n\n१ कोऽपि अन्यः अत्र विज्ञप्तिम् अकरोत् । \n२ पूरातनः कूटशब्दः भवतः/भवत्याः स्मरणे अस्ति ।\n३ भवान्/भवती कूटशब्दं परिवर्तयितुं नेच्छिति ।",
        "passwordreset-emailelement": "सदस्यनाम : \n$1\n\nअल्पकालीनकूटशब्दः : \n$2",
        "passwordreset-emailsentemail": "परिवर्तितकूटशब्दस्य वि-पत्रं प्रेषितम् अस्ति ।",
-       "passwordreset-emailsent-capture": "परिवर्तितकूटशब्दस्य वि-पत्रं प्रेषितम् अस्ति । तत् अधः द्रष्टुं शक्यते ।",
-       "passwordreset-emailerror-capture": "परिवर्तितकूटशब्दस्य वि-पत्रं निर्मितम् अस्ति । तत् अधः द्रष्टुं शक्यते । परन्तु {{GENDER:$2|योजकाय}} प्रेषणकाले तत् निरस्तम् अभवत् : $1",
        "changeemail": "वि-पत्रसङ्केतः परिवर्त्यताम्",
        "changeemail-header": "प्रयोक्तृनाम्नः ई-पत्रसङ्केतः परिवर्त्यताम्",
        "changeemail-no-info": "एतत् पृष्ठं सम्पादयितुं प्रवेशः अनिवार्यः ।",
        "minoredit": "इदं लघु सम्पादनम्",
        "watchthis": "इदं पृष्ठं निरीक्षताम्",
        "savearticle": "पृष्ठं रक्ष्यताम्",
+       "publishpage": "पृष्ठं प्रकाश्यताम्",
+       "publishchanges": "परिवर्तनानि प्रकाश्यन्ताम्",
        "preview": "प्राग्दृश्यम्",
        "showpreview": "प्राग्दृश्यं दृश्यताम्",
        "showdiff": "परिवर्तनानि दृश्यन्ताम्",
        "undo-nochange": "पूर्वमेव एतत् सम्पादनं पूर्ववत् कृतं स्यात् ।",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|talk]]) द्वारा कृता  $1 पूर्ववत्-प्रक्रिया निरस्तीक्रियताम् ।",
        "undo-summary-username-hidden": "निगूहितयोजकद्वारा कृता  $1 पूर्ववत्-प्रक्रिया निरस्तीक्रियताम् ।",
-       "cantcreateaccounttitle": "सदस्यता प्राप्तुं न शक्यते",
        "cantcreateaccount-text": "(<strong>$1</strong>) इत्यस्य संविदः (IP) कृते सदस्यता प्राप्तुं न शक्यते । कारणं [[User:$3|$3]] द्वारा सा संवित्सङ्ख्या प्रतिबन्धिता अस्ति । \n\n$3 इत्यनेन कारणं दत्तं यत्, <em>$2</em>",
        "cantcreateaccount-range-text": "सदस्यताप्राप्तेः सीमा-आक्रान्तृषु <strong>$1</strong> अन्तर्जालसंवित्सु (IP) भवतः/भवत्याः अन्तर्जालसंवद् (<strong>$4</strong>) अन्तर्भवति । अतः [[User:$3|$3]] द्वारा भवतः/भवत्याः अन्तर्जालसंविद् प्रतिबन्धिता ।\n\n$3 इत्यनेन कारणं दत्तं यत्, <em>$2</em>",
        "viewpagelogs": "अस्य पृष्ठस्य संरक्षिताऽऽवलिः (logs) दृश्यताम्",
        "tooltip-ca-nstab-category": "वर्गाणां पृष्ठं दृश्यताम्",
        "tooltip-minoredit": "लघुसम्पादनत्वेन इदं सम्पादनम् अङ्क्यताम्",
        "tooltip-save": "परिवर्तनानि रक्ष्यन्ताम्",
+       "tooltip-publish": "स्वपरिवर्तनानि प्रकश्यन्ताम्",
        "tooltip-preview": "भवता/भवत्या कृतानां परिवर्तनानां प्राग्दृश्यं दृश्यताम्, रक्षणात्पूर्वं कृपया इदम् उपयुज्यताम्।",
        "tooltip-diff": "भवता/भवत्या कृतानि परिवर्तनानि अत्र द्रष्टुं शक्यते",
        "tooltip-compareselectedversions": "पृष्ठस्य द्वयोः चितयोः आवृत्त्योः भेदः दृश्यताम्",
        "special-characters-title-endash": "en dash",
        "special-characters-title-emdash": "em dash",
        "special-characters-title-minus": "minus sign",
-       "mw-widgets-titleinput-description-new-page": "पृष्ठं न विद्यते",
-       "api-error-blacklisted": "कृपया भिन्नं विवरणपूर्वकं शीर्षकं चीयताम् ।"
+       "mw-widgets-titleinput-description-new-page": "पृष्ठं न विद्यते"
 }
index 985eaa0..152a08a 100644 (file)
        "passwordreset-emailtext-user": "Uiser $1 oan {{SITENAME}} requested ae reset o yer passwaird fer {{SITENAME}}\n($4). The follaein uiser {{PLURAL:$3|accoont is|accoonts ar}} associated wi this wab-mail address:\n\n$2\n\n{{PLURAL:$3|This temperie passwaird|Thir temperie passwairds}} will expire in {{PLURAL:$5|yin day|$5 days}}.\nYe shid log in n chuise ae new password nou. Gif some ither bodie haes makit this request, or gif ye'v mynded yer oreeginal passwaird, n ye nae langer wish tae chynge it, ye can ignore this message n continue uisin yer auld passwaird.",
        "passwordreset-emailelement": "Uisername: \n$1\n\nTemperie passwaird: \n$2",
        "passwordreset-emailsentemail": "Ae passwaird reset wab-mail haes been sent.",
-       "passwordreset-emailsent-capture": "Ae passwaird reset wab-mail haas been sent, this is shawn ablow.",
-       "passwordreset-emailerror-capture": "Ae passwaird reset wab-mail wis generated, (this is shawn ablow), but sendin it til the {{GENDER:$2|uiser}} failed: $1",
        "changeemail": "Chynge wab-mail address",
        "changeemail-header": "Chynge accoont wab-mail address",
        "changeemail-no-info": "Ye maun be loggit in tae access this page directly.",
        "undo-nochange": "The edit appears tae hae awready been ondone.",
        "undo-summary": "Ondae reveesion $1 bi [[Special:Contributions/$2|$2]] ([[User talk:$2|Tauk]])",
        "undo-summary-username-hidden": "Ondae reveesion $1 bi ae skauk't uiser",
-       "cantcreateaccounttitle": "Canna creaut accoont",
        "cantcreateaccount-text": "Accoont cræftin fae this IP address ('''$1''') haes been blockit bi [[User:$3|$3]].\n\nThe raison fer this, gien bi $3 is ''$2''",
        "cantcreateaccount-range-text": "Accoont cræftin fae IP addresses in the range <strong>$1</strong>, that inclædes yer IP address (<strong>$4</strong>), haes been blockit bi [[User:$3|$3]].\n\nThe raison gien bi $3 is <em>$2</em>",
        "viewpagelogs": "Leuk at logs fer this page",
index 4372c78..273c8a6 100644 (file)
        "minoredit": "Mažos pakeitėms",
        "watchthis": "Keravuotė ton poslapė",
        "savearticle": "Ėšsauguotė poslapi",
+       "publishpage": "Padėrbtė ton poslapi",
+       "publishchanges": "Ožrašītė poslapė pamainīmus",
        "preview": "Parveiza",
        "showpreview": "Ruodītė parveiza",
        "showdiff": "Ruodītė skėrtomus",
        "undo-success": "Keitėms gal būtė atšaukts. Prašuom patėkrėntė palīgėnėma, asonti žemiau, kū patvėrtėntomiet, kū Tamsta šėta ė nuorėt padarītė, ė tumet ėšsauguokit pakeitėmos, asontios žemiau, kū ožbėngtomiet keitėma atšaukėma.",
        "undo-failure": "Keitėms nagal būt atšaukts diel konflėktounantiu tarpėniu pakeitėmu.",
        "undo-summary": "Pargrōžėnams pakeitėms $1, padėrbts nauduotuojė [[Special:Contributions/$2|$2]] ([[User talk:$2|aptarėms]])",
-       "cantcreateaccounttitle": "Nie galam padėrbtė nauduotuojė",
        "cantcreateaccount-text": "Paskīrū kūrėma ėš šėta IP adresa ('''$1''') ožbluokava [[User:$3|$3]].\n\n$3 nuruodīta prīžastis īr ''$2''",
        "cantcreateaccount-range-text": "Nauduotuoju dėrbėms nug IP adresū <strong>$1</strong>, terp katrū prėgol ė Tamstas IP adresos (<strong>$4</strong>), bova ožgints nauduotuojė [[User:$3|$3]].\n\n$3 ožrašė tuokė dingstiː <em>$2</em>",
        "viewpagelogs": "Ruodītė ton poslapė īpatingus notėkėmus",
index 54c4e65..09392ad 100644 (file)
        "passwordreset-emailtext-user": "Korisnik $1 na {{SITENAME}} je zatražio resetiranje vaše lozinke/zaporke za {{SITENAME}}\n($4). Sljedeći {{PLURAL:$3|korisnički račun je|korisnički računi su}} povezani s ovom e-mail adresom:\n\n$2\n\n{{PLURAL:$3|Ova privremena lozinka|Ove privremene lozinke}} će isteći za {{PLURAL:$5|jedan dan|$5 dana}}.\nTrebate se prijaviti i odabrati novu lozinku. Ako je neko drugi napravio ovaj\nzahtjev, ili ako ste se sjetili Vaše originalne lozinke, a ne želite je više promijeniti, \nmožete zanemariti ovu poruku i nastaviti koristiti staru lozinku.",
        "passwordreset-emailelement": "Korisničko ime: \n$1\n\nPrivremena šifra: \n$2",
        "passwordreset-emailsentemail": "Ako je ovo adresa e-pošte s kojom ste registrirali ovaj račun, podsjetnik šifre/lozinke/zaporke će vam biti poslan na vašu adresu e-pošte.",
-       "passwordreset-emailsent-capture": "E-mail za resetiranje lozinke/zaporke je poslan (prikazan dolje).",
-       "passwordreset-emailerror-capture": "E-mail za resetiranje lozinke/zaporke, prikazan dolje, je poslan, ali slanje {{GENDER:$2|korisniku|korisnici|korisniku}} nije uspjelo: $1",
        "changeemail": "Promeni ili ukloni e-adresu",
        "changeemail-header": "Ispunite sljedeći formular da biste promijenili adresu e-pošte. Ako želite ukloniti postojeću adresu e-pošte s vašeg korisničkog računa, pri ispunjavanju formulara, polje nove adrese e-pošte ostavite prazno.",
-       "changeemail-passwordrequired": "Morat ćete unijeti vašu lozinku/zaporku da potvrdite ovu promjenu.",
        "changeemail-no-info": "Morate biti prijavljeni da biste izravno pristupili ovoj stranici.",
        "changeemail-oldemail": "Trenutna e-mail adresa:",
        "changeemail-newemail": "Nova e-mail adresa:",
        "minoredit": "Ovo je manje uređenje",
        "watchthis": "Prati ovu stranicu",
        "savearticle": "Spremi stranicu",
+       "publishpage": "Objavi stranicu",
+       "publishchanges": "Objavi izmjene",
        "preview": "Pregled",
        "showpreview": "Prikaži pregled",
        "showdiff": "Prikaži izmjene",
        "undo-nochange": "Ovo je uređivanje izgleda već bilo poništeno.",
        "undo-summary": "Poništena izmjena $1 [[Special:Contribs/$2|korisnika $2]] ([[User talk:$2|razgovor]])",
        "undo-summary-username-hidden": "Poništi izmjenu $1 od skrivenog korisnika",
-       "cantcreateaccounttitle": "Nije moguće napraviti korisnički račun",
        "cantcreateaccount-text": "Pravljenje korisničkog računa sa ove IP adrese ('''$1''') je blokirano od strane [[User:$3|$3]].\n\nRazlog koji je naveo $3 je ''$2''",
        "cantcreateaccount-range-text": "Stvaranje računa od IP adresa iz pojasa<strong>$1</strong>, koji uključuje vašu IP adresu (<strong>$4</strong>), je blokirao/la [[User:$3|$3]].\n\nRazlog koji je dao/la $3 je <em>$2</em>",
        "viewpagelogs": "Pogledaj protokole ove stranice",
        "tooltip-ca-nstab-category": "Pogledajte stranicu kategorije",
        "tooltip-minoredit": "Označi ovo kao manje uređenje",
        "tooltip-save": "Spremite svoje izmjene",
+       "tooltip-publish": "Objavi svoje izmjene",
        "tooltip-preview": "Pregledajte svoje izmjene. Molimo vas da ovo koristite prije spremanja.",
        "tooltip-diff": "Prikaz izmjena koje ste napravili u tekstu",
        "tooltip-compareselectedversions": "Pogledajte pazlike između dvije selektovane verzije ove stranice.",
index 87c4234..ff8f1de 100644 (file)
@@ -32,7 +32,8 @@
                        "Roonyh",
                        "Matma Rex",
                        "SusithCM",
-                       "Sandaru"
+                       "Sandaru",
+                       1100100
                ]
        },
        "tog-underline": "සබැඳි යටීර කිරීම:",
        "userlogout": "නික්මීම",
        "notloggedin": "ප්‍රවිසී නැත",
        "userlogin-noaccount": "ගිණුමක් නොමැතිද?",
-       "userlogin-joinproject": "{{SITENAME}}හා එක්වන්න",
+       "userlogin-joinproject": "{{SITENAME}} හා එක්වන්න",
        "nologin": "ඔබ හට ගිණුමක් නොමැතිද? '''$1'''.",
        "nologinlink": "ගිණුමක් තනන්න",
        "createaccount": "අලුත් ගිණුමක් තනන්න",
        "passwordreset-emailtext-user": "{{SITENAME}} හි පරිශීලක $1,{{SITENAME}}($4)සඳහා මුරපදය යලි පිහිටුවීමට ඉල්ලා ඇත.\n\n$2\n\n{{PLURAL:$3|මෙම මුරපදය|මෙම මුරපද}}{{PLURAL:$5|එක් දිනකින්|දවස්$5කින්}}කල් ඉකුත් වනු ඇත.\nඔබ දැන් ඇතුළු වී නව මුරපදයක් තේරිය යුතුය.මෙම ඉල්ලීම වෙන කෙනෙකු විසින් හෝ ඔබට ඔබගේ මුල් මුරපදය මතක නම් හෝ ඔබ තව දුරටත් එය වෙනස් කිරීමට අදහස් නොකරයි නම් හෝ ඔබ මෙම පනිවිඩය නොසලකාහැර ඔබගේ පැරණි මුරපදය භාවිතා කරන්න.",
        "passwordreset-emailelement": "පරිශීලක නාමය: \n$1\n\nතාවකාලික මුරපදය: \n$2",
        "passwordreset-emailsentemail": "මුර-පදය නැවත සකස් කිරීම පිළිබඳව විද්‍යුත් තැපෑලක් යවන ලදී.",
-       "passwordreset-emailsent-capture": "මුර-පදය වෙනස් කිරීම පිළිබඳව විද්‍යුත් තැපෑලක් යවන ලදී, එය පහත දැක්වේ.",
-       "passwordreset-emailerror-capture": "සිහිකැඳවුම් ඊ-තැපෑල ජනිත කරනු ලැබූ අතර, එය පහත දැක්වේ, නමුත් එය {{GENDER:$2|}}පරිශීලකයාට යැවීම අසාර්ථක වුනි: $1",
        "changeemail": "විද්‍යුත් තැපෑල වෙනස් කරන්න හෝ ඉවත් කරන්න",
        "changeemail-header": "ගිණුම් විද්‍යුත් තැපැල් ලිපිනය වෙනස් කරන්න",
        "changeemail-no-info": "මෙම පිටුව සෘජු ලෙස සම්ප්‍රවේශය කෙරුමට පළමුව ඔබ ප්‍රවිෂ්ටව සිටිය යුතුය.",
        "undo-nochange": "මෙම සංස්කරණය දැනටමත් අතහැර දමන ලද කර ඇති බව පෙනී යයි.",
        "undo-summary": " [[Special:Contributions/$2|$2]] මගින් සිදුකල  $1 සංශෝධනය අහෝසි කරන්න ([[User talk:$2|සාකච්ඡා]])",
        "undo-summary-username-hidden": "සැඟවුණු පරිශීලකයෙක් විසින් සංශෝධනය $1 අස් කරන්න",
-       "cantcreateaccounttitle": "ගිණුම තැනිය නොහැක",
        "cantcreateaccount-text": "මෙම IP ලිපිනය ('''$1''') මගින් ගිණුම් තැනීම [[User:$3|$3]] විසින් වාරණය කොට ඇත.\n\n$3 විසින් සපයා ඇති හේතුව ''$2'' වේ",
        "cantcreateaccount-range-text": "ඔබේ IP ලිපිනය ('' '$4' '') ද ඇතුළත් වන පරාසය තුළ IP ලිපිනයන් '' '$1', '' සිට ගිණුම් තැනීම  [[User:$3|$3]] විසින් වාරණය කොට ඇත. $3 විසින් දී ඇති හේතුව '' '$2' වේ",
        "viewpagelogs": "මෙම පිටුව පිලිබඳ සටහන් නරඹන්න",
        "special-characters-title-endash": "en තේජස",
        "special-characters-title-emdash": "em තේජස",
        "special-characters-title-minus": "ඍණ ලකුණ",
-       "api-error-blacklisted": "කරුණාකර වෙනස්, විස්තරාත්මක මාතෘකාවක් තෝරන්න.",
        "randomrootpage": "අහඹු මූල පිටුව"
 }
index 4f1d008..d1f7ea4 100644 (file)
        "passwordreset-emailelement": "Uporabniško ime: \n$1\n\nZačasno geslo: \n$2",
        "passwordreset-emailsentemail": "Če je e-poštni naslov povezan z vašim računom, vam bomo poslali e-pošto za postavitev gesla.",
        "passwordreset-emailsentusername": "Če obstaja e-poštni naslov, povezan s tem uporabniškim imenom, vam bomo poslali e-pošto za postavitev gesla.",
-       "passwordreset-emailsent-capture": "Poslali smo e-pošto za ponastavitev gesla, ki je prikazana spodaj.",
-       "passwordreset-emailerror-capture": "Ustvarili smo e-pošto za ponastavitev gesla, ki je prikazana spodaj, vendar pa pošiljanje {{GENDER:$2|uporabniku|uporabnici}} ni uspelo: $1",
        "passwordreset-emailsent-capture2": "Poslali smo {{PLURAL:$1|e-pošto|e-pošti|e-pošte}} za ponastavitev gesla. {{PLURAL:$1|Uporabniško ime in geslo sta navedena spodaj.|Seznam uporabniških imen in gesel je naveden spodaj.}}",
        "passwordreset-emailerror-capture2": "Pošiljanje e-pošte {{GENDER:$2|uporabniku|uporabnici}} je spodletelo: $1 {{PLURAL:$3|Uporabniško ime in geslo sta navedena spodaj.|Seznam uporabniških imen in gesel je naveden spodaj.}}",
        "passwordreset-nocaller": "Podati morate klicatelja",
        "passwordreset-nodata": "Navedli niste ne uporabniškega imena ne e-poštnega naslova",
        "changeemail": "Sprememba ali odstranitev e-poštnega naslova",
        "changeemail-header": "Izpolnite obrazec za spremembo vašega e-poštnega naslova. Če želite s svojega računa odstraniti povezavo s katerim koli e-poštnim naslovom, pustite polje za nov e-poštni naslov med potrjevanje obrazca prazno.",
-       "changeemail-passwordrequired": "Za potrditev spremembe boste morali vnesti svoje geslo.",
        "changeemail-no-info": "Za neposredni dostop do strani morate biti prijavljeni.",
        "changeemail-oldemail": "Trenutni e-poštni naslov:",
        "changeemail-newemail": "Novi e-poštni naslov:",
        "undo-nochange": "Zdi se, da je urejanje nekdo že razveljavil.",
        "undo-summary": "Redakcija $1 uporabnika [[Special:Contributions/$2|$2]] ([[User talk:$2|pogovor]]) razveljavljena",
        "undo-summary-username-hidden": "Razveljavi redakcijo $1 skritega uporabnika",
-       "cantcreateaccounttitle": "Računa ni moč ustvariti",
        "cantcreateaccount-text": "Registracije z IP-naslova ('''$1''') je administrator(ka) [[User:$3|$3]] blokiral(a).\n\nRazlog, ki ga je $3 podal(a), je ''$2''.",
        "cantcreateaccount-range-text": "Ustvarjanje računov z IP-naslovov v območju <strong>$1</strong>, ki vključuje vaš IP-naslov (<strong>$4</strong>), je blokiral(-a) [[User:$3|$3]].\n\nRazlog, ki ga je podal(-a) $3, je <em>$2</em>.",
        "viewpagelogs": "Poglej dnevniške zapise o strani",
        "uploadstash-errclear": "Čiščenje datotek je spodletelo.",
        "uploadstash-refresh": "Osveži seznam datotek",
        "uploadstash-thumbnail": "ogled sličice",
+       "uploadstash-exception": "Nalaganja nismo uspeli shraniti v zalogo ($1): »$2«.",
        "invalid-chunk-offset": "Neveljaven odmik delčka",
        "img-auth-accessdenied": "Dostop zavrnjen",
        "img-auth-nopathinfo": "Manjka PATH_INFO.\nVaš strežnik ne poda te informacije.\nMorda temelji na CGI in ne more podpirati img_auth.\nOglejte si  https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization.",
        "undeletehistorynoadmin": "Stran je bila izbrisana.\nRazlog za izbris je skupaj s podrobnostmi o uporabnikih, ki so jo urejali pred izbrisom, naveden v prikazanem povzetku.\nDejansko besedilo izbrisanih redakcij je dostopno le administratorjem.",
        "undelete-revision": "Izbrisana redakcija $1 (dne $4 ob $5) uporabnika $3:",
        "undeleterevision-missing": "Napačna ali manjkajoča redakcija.\nMorda imate napačno povezavo ali pa je bila redakcija obnovljena ali odstranjena iz arhiva.",
+       "undeleterevision-duplicate-revid": "$1 {{PLURAL:$1|redakcije|redakcij}} nismo mogli obnoviti, saj je bil {{PLURAL:$1|1=njen|njihov}} <code>rev_id</code> že v uporabi.",
        "undelete-nodiff": "Predhodnih različic ne najdem.",
        "undeletebtn": "Obnovi",
        "undeletelink": "poglej/obnovi",
        "undeletedrevisions": "{{PLURAL:$1|obnovljena $1 redakcija|obnovljeni $1 redakciji|obnovljene $1 redakcije|obnovljenih $1 redakcij}}",
        "undeletedrevisions-files": "$1 {{PLURAL:$1|redakcija|redakciji|redakcije|redakcij}} in $2 {{PLURAL:$2|datoteka|datoteki|datoteke|datotek}} {{PLURAL:$1+$2|obnovljena|obnovljeni|obnovljene|obnovljenih}}",
        "undeletedfiles": "{{PLURAL:$1|obnovljena je $1 datoteka|obnovljeni sta $1 datoteki|obnovljene so $1 datoteke|obnovljenih je $1 datotek}}",
-       "cannotundelete": "Obnova je spodletela:\n$1",
+       "cannotundelete": "Nekatere ali vse obnove so spodletele:\n$1",
        "undeletedpage": "'''Obnovili ste stran $1.'''\n\nNedavna brisanja in obnove so zapisani v [[Special:Log/delete|dnevniku brisanja]].",
        "undelete-header": "Glej [[Special:Log/delete|dnevnik brisanja]] za nedavno izbrisane strani.",
        "undelete-search-title": "Iskanje izbrisanih strani",
        "sp-contributions-newbies-sub": "Prispevki novincev",
        "sp-contributions-newbies-title": "Uporabniški prispevki novih računov",
        "sp-contributions-blocklog": "dnevnik blokiranja",
-       "sp-contributions-suppresslog": "zatrti uporabnikovi prispevki",
-       "sp-contributions-deleted": "izbrisani uporabnikovi prispevki",
+       "sp-contributions-suppresslog": "zatrti {{GENDER:$1|uporabnikovi|uporabničini}} prispevki",
+       "sp-contributions-deleted": "izbrisani zatrti {{GENDER:$1|uporabnikovi|uporabničini}} prispevki",
        "sp-contributions-uploads": "naložene datoteke",
        "sp-contributions-logs": "dnevniki",
        "sp-contributions-talk": "pogovor",
index 0d938b6..fce5916 100644 (file)
        "passwordreset-emailtext-ip": "(Qof laga yaabo in ee tahay adi, oo ka socdo ciwaanka IP'ka $1)  ayaa  codsaday xasuus faah faahin akoonkaada {{SITENAME}}\n($4). Isticmaaladaan soo socota {{PLURAL:$3|akoonkooda waxee|akoonkooda waxee}} la xiriiraan ciwaankaan e-mailka ah:\n\n$2\n\n{{PLURAL:$3|eraysirkaan kumeel gaarka ah|Eraysiryadaan kumeel gaarka ah}} waxay dhacaayaan {{PLURAL:$5|hal maalin|$5 maalmood}}.\nWaa in aad gudaha gashaa oo e-mail cusub doorataa hadda. Hadii ee qof kale codsigaan sameysay, ama hadii aad soo xasuusatay eraysirkaagii hore, oo aadna u baahneen in aad badashid, iska ilaaw fariintaan siina isticmaal eraysirkaagii duqi ahaa.",
        "passwordreset-emailtext-user": "Isticmaale $1 ee {{SITENAME}} wuxuu codsaday xasuus faah faahin akoonkaada {{SITENAME}}\n($4). Isticmaaladaan soo socota {{PLURAL:$3|akoonkooda waxee|akoonkooda waxee}} la xiriiraan ciwaankaan e-mailka ah:\n\n$2\n\n{{PLURAL:$3|eraysirkaan kumeel gaarka ah|Eraysiryadaan kumeel gaarka ah}} waxay dhacaayaan {{PLURAL:$5|hal maalin|$5 maalmood}}.\nWaa in aad gudaha gashaa oo e-mail cusub doorataa hadda. Hadii ee qof kale codsigaan sameysay, ama hadii aad soo xasuusatay eraysirkaagii hore, oo aadna u baahneen in aad badashid, iska ilaaw fariintaan siina isticmaal eraysirkaagii duqi ahaa.",
        "passwordreset-emailelement": "Magaca gudagalka: \n$1\n\nEreysirka kumeelgaarka ah: \n$2",
-       "passwordreset-emailerror-capture": "E-mail xasuus ah ayaa la sameeyay, oo ka arki kartid hoosta,laakiin wuxuu ku guul dareestay in isticmaalaha loo diro: $1",
        "changeemail": "Bedel ciwaanka E-mailka",
        "changeemail-header": "Bedel ciwaanka e-mailka akoonka",
        "changeemail-oldemail": "Ciwaanka e-mailka hadda jiro:",
        "post-expand-template-inclusion-category": "Boggaga ku xad gudbay weyninka tusmo'da",
        "post-expand-template-argument-warning": "'''Digniin:'''Boggaan waxaa ku jira ugu yaraan hal iyo wixii ka badan oo template ah, waxaana ku xiran kuwa kale.",
        "undo-summary": "Noqay bedelaadka $1 ee sameeyay  [[Special:Contributions/$2|$2]] ([[User talk:$2|hadal]])",
-       "cantcreateaccounttitle": "Ma' sameynkaro gudagal (akoon)",
        "cantcreateaccount-text": "Akoon'ka sameeyaha leh ciwaankaan  IP:ka ('''$1''') waxaa mamnuucay [[User:$3|$3]].\n\nSababta uu qoray $3 waa ''$2''",
        "viewpagelogs": "Fiiri guadagalayaasha boggaan",
        "nohistory": "Boggaan malahan taariikhda bedelaadka",
index 277baa3..c82f7ff 100644 (file)
        "tog-watchdeletion": "Shto faqet dhe skedat e grisura prej meje tek lista e faqeve  nën mbikqyrje",
        "tog-watchrollback": "Shto faqet ku unë kam kryer një rikthim tek lista ime mbikqyrëse",
        "tog-minordefault": "Shëno të gjitha redaktimet si të vogla automatikisht",
-       "tog-previewontop": "Vendose kutinë e bocetit sipër kutisë së redaktimeve",
-       "tog-previewonfirst": "Trego se si do të duket faqja pos ta filloj redaktimin",
-       "tog-enotifwatchlistpages": "Më njofto me email kur ndryshohet një faqe apo skedë nga lista ime e faqeve nën mbikqyrje",
-       "tog-enotifusertalkpages": "Kur faqja ime e diskutimeve e përdoruesit ndryshohet, më dërgo email",
-       "tog-enotifminoredits": "Më njofto me e-mail edhe kur ka redaktime të vogla në faqe dhe skedave",
-       "tog-enotifrevealaddr": "Tregoje adresën time të e-mail-it në e-mail-et njoftuese",
+       "tog-previewontop": "Trego se si do të duket faqja mbi kutinë redaktimit",
+       "tog-previewonfirst": "Trego se si do të duket faqja posa ta filloj redaktimin",
+       "tog-enotifwatchlistpages": "Më njofto me email kur ndryshohet një faqe apo skedë nga lista ime e faqeve nën vëzhgim",
+       "tog-enotifusertalkpages": "Më dërgo email kur ndryshohet faqja ime e diskutimeve",
+       "tog-enotifminoredits": "Më njofto me email edhe kur ka redaktime të vogla të faqeve dhe skedave",
+       "tog-enotifrevealaddr": "Trego adresën time të emailit në emailet njoftuese",
        "tog-shownumberswatching": "Trego numrin e përdoruesve që vëzhgojnë këtë faqe",
        "tog-oldsig": "Nënshkrimi ekzistues:",
        "tog-fancysig": "Mbaje nënshkrimin si wikitekst (pa lidhje automatike)",
-       "tog-uselivepreview": "Trego pamjen në mënyrë të drejtëpërdrejtë",
-       "tog-forceeditsummary": "Më njofto kur e lë përmbledhjen e redaktimit bosh",
+       "tog-uselivepreview": "Trego parapamjen drejtpërdrejt",
+       "tog-forceeditsummary": "Më njofto kur përmbledhjen e redaktimit e lë bosh",
        "tog-watchlisthideown": "Fshih redaktimet e mia nga lista e faqeve të vëzhguara",
        "tog-watchlisthidebots": "Fshih redaktimet e robotëve nga lista e faqeve të vëzhguara",
        "tog-watchlisthideminor": "Fshih redaktimet e vogla nga lista e faqeve të vëzhguara",
        "laggedslavemode": "'''Kujdes:''' Kjo faqe nuk mund të ketë përditësime të kohëve të fundit.",
        "readonly": "Databaza e kyçur",
        "enterlockreason": "Shëno arsyen e kyçjes, gjithashtu shëno se kur mund të hapet.",
-       "readonlytext": "Databaza është për momentin e kyçur, nuk lejohen ndryshime ose modifikime, ndoshta për shkak të rutinës së mirëmbajtjes. Pas përfundimit të mirëmbajtjes databaza do të hapet përsëri.\n\nAdministratori që e kyçi dha këtë arsye: $1",
+       "readonlytext": "Databaza për momentin është mbyllur për redaktime dhe ndryshime të reja, ndoshta për shkak të rutinës së mirëmbajtjes. Pas përfundimit të mirëmbajtjes databaza do të hapet përsëri.\n\nAdministratori që e mbylli dha këtë arsye: $1",
        "missing-article": "Databaza nuk gjeti dot tekstin e faqes që duhet të kishte gjetur me emër \"$1\" $2.\n\nKjo zakonisht vjen si rezultat i një diff-i të vjetëruar ose të ndonjë lidhjeje në historikun e një faqeje që është fshirë.\n\nNëse nuk është kjo arsyeja, ateherë ju mund të keni gjetur një gabim në program. Ju lutemi, njoftoni një [[Special:ListUsers/sysop|administrator]], tregojini URL-në problematike.",
        "missingarticle-rev": "(rishikim#: $1)",
        "missingarticle-diff": "(Diff: $1, $2)",
        "passwordreset-emailtext-user": "Përdoruesi  $1 në {{SITENAME }} ka kërkuar një kujtesë për të dhënat e llogarisë suaj për {{SITENAME }} ($4). Përdoruesi në vijim {{PLURAL:$3 | llogaria është | llogaritë janë}} të lidhur me këtë postë elektronike: \n\n$2\n\n{{PLURAL:$3 | Ky fjalëkalim i përkohshëm | Këto fjalëkalime të përkohshme}} do të përfundojë në {{PLURAL:$5 | një ditë | $5 ditë}}.\nJu duhet të kyçeni dhe të zgjidhni një fjalëkalim të ri tani. Nëse dikush tjetër e ka bërë këtë kërkesës, ose në qoftë se ju mbani mend fjalëkalimin tuaj origjinal, dhe ju nuk dëshirojni të ndryshoni atë, ju mund të injoroni këtë mesazh dhe do të vazhdoni përdorimin e fjalëkalimit tuaj të vjetër.",
        "passwordreset-emailelement": "Emri i përdoruesit: \n$1\n\nFjalëkalimi i përkohshëm: \n$2",
        "passwordreset-emailsentemail": "Nëse kjo është një adresë emaili e regjistruar për llogarinë tuaj, atëherë një email për rivendosjen e fjalëkalimit do të dërgohet.",
-       "passwordreset-emailsent-capture": "Një email për rivendosjen e fjalëkalimit është dërguar, i cili tregohet më poshtë.",
-       "passwordreset-emailerror-capture": "U dërgua një e-mail kujtesë, i cili tregohet më poshtë, por dërgesa për tek përdoruesi qe e pamundur: $1",
        "changeemail": "Ndrysho ose hiq postën elektronike",
        "changeemail-header": "Ndrysho llogarinë e adresës së postës elektronike",
        "changeemail-no-info": "Ju duhet të identifikoheni në mënyrë që të keni të drejtë hyrjeje në këtë faqe.",
        "undo-failure": "Redaktimi nuk mund të zhbëhet për shkak të redaktimeve konfliktuese të ndërmjetshme.",
        "undo-norev": "Redaktimi nuk mund të zhbëhet sepse nuk ekziston ose është fshirë.",
        "undo-summary": "Zhbëje versionin $1 i bërë nga [[Special:Contributions/$2|$2]] ([[User talk:$2|ligjëratë]])",
-       "cantcreateaccounttitle": "Nuk mundet të krijohet llogaria",
        "cantcreateaccount-text": "Hapja e llogarive nga kjo adresë IP ('''$1''') është bllokuar nga [[User:$3|$3]].\n\nArsyeja e dhënë nga $3 është ''$2''.",
        "viewpagelogs": "Shiko regjistrat për këtë faqe",
        "nohistory": "Nuk ka histori redaktimesh për këtë faqe.",
index 3867416..26b3ffd 100644 (file)
        "passwordreset-emailelement": "Корисничко име: \n$1\n\nПривремена лозинка: \n$2",
        "passwordreset-emailsentemail": "Ако је ово имејл адреса повезана са Вашим налогом, подсетник о лозинци ће бити послат на имејл.",
        "passwordreset-emailsentusername": "Ако сте навели имејл адресу приликом регистрације, биће послат имејл за ресетовање лозинке.",
-       "passwordreset-emailsent-capture": "Послат је подсетник преко имејла, који је приказан доле.",
-       "passwordreset-emailerror-capture": "Имејл за ресетовање лозинке, приказан испод је послат, али слање {{GENDER:$2|кориснику|корисници}} није успело: $1",
        "changeemail": "Промени или уклони имејл адресу",
        "changeemail-header": "Попуните овај образац да би сте променили Вашу имејл адресу. Ако жели да ускратите приступ било којој имејл адреси Вашем налогу, оставите празно поље за нову имејл адресу приликом попуњавање обрасца.",
-       "changeemail-passwordrequired": "Морате унети лозинку да би потврдили ову измену.",
        "changeemail-no-info": "Морате бити пријављени да бисте приступили овој страници.",
        "changeemail-oldemail": "Тренутна имејл адреса:",
        "changeemail-newemail": "Нова имејл адреса:",
        "undo-nochange": "Изгледа да је измена већ поништена.",
        "undo-summary": "Поништена измена $1 {{GENDER:$2|корисника|кориснице}} [[Special:Contribs/$2|$2]] ([[User talk:$2|разговор]])",
        "undo-summary-username-hidden": "Поништи измену $1 скривеног корисника",
-       "cantcreateaccounttitle": "Не могу да отворим налог",
        "cantcreateaccount-text": "Отварање налога с ове ИП адресе (<strong>$1</strong>) је блокирао/ла [[User:$3|$3]].\n\nРазлог који је навео/ла $3 је <em>$2</em>",
        "cantcreateaccount-range-text": "Отварање налога са ИП адреса у распону <strong>$1</strong>, који укључује и вашу ИП адресу (<strong>$4</strong>) је блокирао/ла [[User:$3|$3]].\n\nРазлог који је навео/ла $3 је <em>$2</em>",
        "viewpagelogs": "Погледај дневнике ове странице",
        "protectlogpage": "Дневник закључавања",
        "protectlogtext": "Испод је списак заштићених страница.\nПогледајте [[Special:ProtectedPages|списак заштићених страница]] за више детаља.",
        "protectedarticle": "је заштитио „[[$1]]“",
-       "modifiedarticleprotection": "је променио степен заштите за „[[$1]]“",
+       "modifiedarticleprotection": "промењен степен заштите за „[[$1]]“",
        "unprotectedarticle": "је скинуо заштиту са странице „[[$1]]“",
        "movedarticleprotection": "је преместио поставке заштите са „[[$2]]“ на „[[$1]]“",
        "protect-title": "Степен заштите за „$1“",
index 9d11bc5..155e8c6 100644 (file)
        "passwordreset-emailelement": "Korisničko ime: \n$1\n\nPrivremena lozinka: \n$2",
        "passwordreset-emailsentemail": "Podsetnik o lozinci je poslat na vašu adresu.",
        "passwordreset-emailsentusername": "Ako ste naveli imejl adresu prilikom registracije, biće poslat imejl za resetovanje lozinke.",
-       "passwordreset-emailsent-capture": "Poslat je podsetnik preko e-pošte (prikazan dole).",
-       "passwordreset-emailerror-capture": "E-poruka za resetovanje lozinke, prikazana ispod je poslata, ali slanje {{GENDER:$2|korisniku|korisnici}} nije uspelo: $1",
        "changeemail": "Promeni ili ukloni e-adresu",
        "changeemail-header": "Promenite e-adresu naloga",
-       "changeemail-passwordrequired": "Morate uneti lozinku da bi potvrdili ovu izmenu.",
        "changeemail-no-info": "Morate biti prijavljeni da biste pristupili ovoj stranici.",
        "changeemail-oldemail": "Trenutna e-adresa:",
        "changeemail-newemail": "Nova e-adresa:",
        "undo-nochange": "Izgleda da je izmena već poništena.",
        "undo-summary": "Poništena izmena $1 {{GENDER:$2|korisnika|korisnice}} [[Special:Contribs/$2|$2]] ([[User talk:$2|razgovor]])",
        "undo-summary-username-hidden": "Poništi izmenu $1 skrivenog korisnika",
-       "cantcreateaccounttitle": "Ne mogu da otvorim nalog",
        "cantcreateaccount-text": "Otvaranje naloga s ove IP adrese (<strong>$1</strong>) je blokirao/la [[User:$3|$3]].\n\nRazlog koji je naveo/la $3 je <em>$2</em>",
        "cantcreateaccount-range-text": "Otvaranje naloga sa IP adresa u rasponu <strong>$1</strong>, koji uključuje i vašu IP adresu (<strong>$4</strong>) je blokirao/la [[User:$3|$3]].\n\nRazlog koji je naveo/la $3 je <em>$2</em>",
        "viewpagelogs": "Pogledaj dnevnike ove stranice",
        "protectlogpage": "Dnevnik zaključavanja",
        "protectlogtext": "Ispod je spisak zaštićenih stranica.\nPogledajte [[Special:ProtectedPages|spisak zaštićenih stranica]] za više detalja.",
        "protectedarticle": "je zaštitio „[[$1]]“",
-       "modifiedarticleprotection": "je promenio stepen zaštite za „[[$1]]“",
+       "modifiedarticleprotection": "promenjen stepen zaštite za „[[$1]]“",
        "unprotectedarticle": "je skinuo zaštitu sa stranice „[[$1]]“",
        "movedarticleprotection": "je premestio postavke zaštite sa „[[$2]]“ na „[[$1]]“",
        "protect-title": "Stepen zaštite za „$1“",
index 941db3c..4e5103f 100644 (file)
@@ -72,7 +72,8 @@
                        "Mgr",
                        "Matma Rex",
                        "McDutchie",
-                       "Larske"
+                       "Larske",
+                       "Rockyfelle"
                ]
        },
        "tog-underline": "Stryk under länkar:",
        "tagline": "Från {{SITENAME}}",
        "help": "Hjälp",
        "search": "Sök",
-       "search-ignored-headings": "#<!-- lämna denna rad precis som den är --> <pre>\n# Rubriker som kommer att ignoreras av sökningen.\n# Ändringar till detta kommer att gälla så fort sidan med rubriken är indexerad.\n# Du kan tvinga sidan att indexeras om genom att göra en null-redigering.\n# Syntaxen är som följer:\n#  * Allt från ett \"#\" tecken till slutet av raden är en kommentar.\n#  * Varje icke-tom rad är den exakta titeln som ska ignoreras, shiftläge och allt.\nReferenser\nKällor\nExterna länkar\nSe även\n #</pre> <!-- lämna denna rad precis som den är -->",
+       "search-ignored-headings": "#<!-- lämna denna rad precis som den är --> <pre>\n# Rubriker som kommer att ignoreras av sökningen.\n# Ändringar till detta kommer att gälla så fort sidan med rubriken är indexerad.\n# Du kan tvinga sidan att indexeras om genom att göra en null-redigering.\n# Syntaxen är som följer:\n#  * Allt från ett \"#\" tecken till slutet av raden är en kommentar.\n#  * Varje icke-tom rad är den exakta titeln som ska ignoreras, shiftläge och allt.\nReferenser\nExterna länkar\nSe även\n #</pre> <!-- lämna denna rad precis som den är -->",
        "searchbutton": "Sök",
        "go": "Gå till",
        "searcharticle": "Gå till",
        "passwordreset-emailelement": "Användarnamn: \n$1\n\nTillfälligt lösenord: \n$2",
        "passwordreset-emailsentemail": "Om denna e-postadress är associerad med ditt konto kommer en lösenordsåterställning skickas via e-post.",
        "passwordreset-emailsentusername": "Om det finns en e-postadress som associeras med detta användarnamn kommer en lösenordsåterställning skickas via e-post.",
-       "passwordreset-emailsent-capture": "En lösenordsåterställning via e-post har skickats, som visas nedan.",
-       "passwordreset-emailerror-capture": "En lösenordsåterställning via e-post har skapats, som visas nedan, men det gick inte att skicka den till {{GENDER:$2|användaren}}: $1",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|E-postmeddelande|E-postmeddelanden}} för återställning av lösenord har skickats. {{PLURAL:$1|Användarnamnet och lösenordet|Listan över användarnamn och lösenord}} visas nedan.",
        "passwordreset-emailerror-capture2": "Kunde inte skicka e-post till {{GENDER:$2|användaren}}: $1 {{PLURAL:$3|Användarnamnet och lösenordet|Listan över användarnamn och lösenord}} listas nedan.",
        "passwordreset-nocaller": "En användare måste anges",
        "passwordreset-invalideamil": "Ogiltig e-postadress",
        "passwordreset-nodata": "Varken ett användarnamn eller en e-postadress angavs",
        "changeemail": "Ändra eller ta bort e-postadress",
-       "changeemail-header": "Fyll i detta formulär för att ändra din e-postadress. Lämna fältet för ny e-postadress tomt när du skickar in formuläret om du vill ta bort en associerad e-postadress från ditt konto.",
-       "changeemail-passwordrequired": "Du måste ange ditt lösenord för att bekräfta denna ändring.",
+       "changeemail-header": "Fyll i detta formulär för att ändra din e-postadress. Om du vill ta bort en associerad e-postadress från ditt konto lämnar du fältet för ny e-postadress tomt när formuläret skickas in.",
        "changeemail-no-info": "Du måste vara inloggad för att komma åt den här sidan direkt.",
        "changeemail-oldemail": "Nuvarande e-postadress:",
        "changeemail-newemail": "Ny e-postadress:",
        "anontalkpagetext": "----<em>Detta är diskussionssidan för en anonym användare som inte ännu skapat ett konto, eller som inte använder det.</em>\nDärför måste vi använda den numeriska IP-adressen för att identifiera honom/henne.\nEn sådan IP-adress kan delas av flera användare.\nOm du är en anonym användare och känner att irrelevanta kommentarer har riktats mot dig, vänligen [[Special:CreateAccount|skapa ett konto]] eller [[Special:UserLogin|logga in]] för att undvika framtida förväxlingar med andra anonyma användare.",
        "noarticletext": "Det finns just nu ingen text på denna sida.\nDu kan [[Special:Search/{{PAGENAME}}|söka efter denna sidtitel]] på andra sidor, <span class=\"plainlinks\">[{{fullurl:{{#Special:Log}}|page={{FULLPAGENAMEE}}}} söka i relaterade loggar], eller [{{fullurl:{{FULLPAGENAME}}|action=edit}} skapa denna sida]</span>.",
        "noarticletext-nopermission": "Det finns för tillfället ingen text på denna sida.\nDu kan [[Special:Search/{{PAGENAME}}|söka efter denna sidas titel]] på andra sidor,\neller <span class=\"plainlinks\">[{{fullurl:{{#Special:Log}}|page={{FULLPAGENAMEE}}}} söka i relaterade loggar]</span> men du har inte behörighet att skapa sidan.",
-       "missing-revision": "Revisionen #$1 av sidan med namnet \"{{FULLPAGENAME}}\" finns inte.\n\nDetta orsakas vanligen av efter en gammal historiklänk till en sida som har raderats.\nDetaljer kan hittas i [{{fullurl:{{#Special:Log}}/delete|page={{FULLPAGENAMEE}}}} raderingsloggen].",
+       "missing-revision": "Version #$1 av sidan med namnet \"{{FULLPAGENAME}}\" finns inte.\n\nDetta orsakas vanligen genom att en gammal historiklänk följts till en sida som har raderats.\nDetaljer kan hittas i [{{fullurl:{{#Special:Log}}/delete|page={{FULLPAGENAMEE}}}} raderingsloggen].",
        "userpage-userdoesnotexist": "\"<nowiki>$1</nowiki>\" är inte ett registrerat användarkonto. Tänk efter om du vill skapa/redigera den här sidan.",
        "userpage-userdoesnotexist-view": "Kontot \"$1\" är inte registrerat.",
        "blocked-notice-logextract": "Användaren är blockerad.\nOrsaken till senaste blockeringen kan ses nedan:",
        "undo-nochange": "Det verkar som att redigeringen redan har blivit ogjord.",
        "undo-summary": "Gör version $1 av [[Special:Contributions/$2|$2]] ([[User talk:$2|diskussion]]) ogjord",
        "undo-summary-username-hidden": "Gör version $1 av en dold användare ogjord",
-       "cantcreateaccounttitle": "Kan inte skapa konto",
        "cantcreateaccount-text": "[[User:$3|$3]] har blockerat den här IP-adressen ('''$1''') från att registrera konton.\n\nAnledningen till blockeringen var \"$2\".",
        "cantcreateaccount-range-text": "IP-adresserna i intervallet <strong>$1</strong>, som inkluderar din IP-adress (<strong>$4</strong>), har blockerats från att skapa konton av [[User:$3|$3]].\n\nAnledningen enligt $3 var <em>$2</em>",
        "viewpagelogs": "Visa loggar för denna sida",
        "revdelete-selected-text": "{{PLURAL:$1|Vald version|Valda versioner}} av [[:$2]]:",
        "revdelete-selected-file": "{{PLURAL:$1|Vald filversion|Valda filversioner}} av [[:$2]]:",
        "logdelete-selected": "{{PLURAL:$1|Vald loggåtgärd|Valda loggåtgärder}}:",
-       "revdelete-text-text": "Raderade sidversioner kommer fortfarande synas i sidans historik, men delar av innehållet kommer inte att bli tillgängligt offentligt.",
+       "revdelete-text-text": "Raderade sidversioner kommer fortfarande synas i sidans historik, men delar av innehållet kommer inte att vara tillgängligt offentligt.",
        "revdelete-text-file": "Raderade filversioner kommer fortfarande synas i filens historik, men delar av innehållet kommer inte att bli tillgängligt offentligt.",
        "logdelete-text": "Raderade logghändelser kommer fortfarande synas i loggarna, men delar av innehållet kommer inte att bli tillgängligt offentligt.",
        "revdelete-text-others": "Andra administratörer kommer fortfarande att kunna komma åt det dolda innehållet och återställa det igen om inte ytterligare begränsningar används.",
        "prefs-email": "Alternativ för e-post",
        "prefs-rendering": "Utseende",
        "saveprefs": "Spara",
-       "restoreprefs": "Återgå till standardinställningar",
+       "restoreprefs": "Återgå till standardinställningar (i alla delar)",
        "prefs-editing": "Redigering",
        "rows": "Rader:",
        "columns": "Kolumner:",
        "recentchanges-legend-plusminus": "(''±123'')",
        "recentchanges-submit": "Visa",
        "rcnotefrom": "Nedan visas {{PLURAL:$5|ändringen|ändringar}} sedan <strong>$3, $4</strong> (upp till <strong>$1</strong> ändringar visas).",
-       "rclistfrom": "Visa ändringar från och med $2 $3",
+       "rclistfrom": "Visa nya ändringar från och med $2 $3",
        "rcshowhideminor": "$1 mindre ändringar",
        "rcshowhideminor-show": "Visa",
        "rcshowhideminor-hide": "Dölj",
        "uploadstash-errclear": "Rensning av filerna misslyckades.",
        "uploadstash-refresh": "Uppdatera listan över filer",
        "uploadstash-thumbnail": "visa miniatyr",
+       "uploadstash-exception": "Kunde inte lagra uppladdning i stash ($1): \"$2\".",
        "invalid-chunk-offset": "Ogiltig segmentsförskjutning",
        "img-auth-accessdenied": "Åtkomst nekad",
        "img-auth-nopathinfo": "PATH_INFO saknas.\nDin server är inte inställd för att ge denna information.\nDen kan vara CGI-baserad och stöder inte img_auth.\n[https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization Se bildbehörighet.]",
        "watchnologin": "Inte inloggad",
        "addwatch": "Lägg till i bevakningslistan",
        "addedwatchtext": "\"[[:$1]]\" har lagts till i din [[Special:Watchlist|bevakningslista]].",
+       "addedwatchtext-talk": "\"[[:$1]]\" och dess associerade sida har lagts till i din [[Special:Watchlist|bevakningslista]].",
        "addedwatchtext-short": "Sidan \"$1\" har lagts till i din bevakningslista.",
        "removewatch": "Ta bort från bevakningslistan",
        "removedwatchtext": "\"[[:$1]]\" och dess diskussionssida har tagits bort från [[Special:Watchlist|din bevakningslista]].",
+       "removedwatchtext-talk": "\"[[:$1]]\" och dess associerade sida har tagits bort från din [[Special:Watchlist|bevakningslista]].",
        "removedwatchtext-short": "Sidan \"$1\" har tagits bort från din bevakningslista.",
        "watch": "Bevaka",
        "watchthispage": "Bevaka denna sida",
        "undeletehistorynoadmin": "Den här sidan har blivit raderad. Anledningen till detta anges i sammanfattningen nedan, tillsammans med uppgifter om de användare som redigerat sidan innan den raderades. Enbart administratörerna har tillgång till den raderade texten.",
        "undelete-revision": "Raderad version av $1 (från den $4 kl. $5) av $3.",
        "undeleterevision-missing": "Versionen finns inte eller är felaktig. Versionen kan ha återställts eller tagits bort från arkivet, du kan också ha följt en felaktig länk.",
+       "undeleterevision-duplicate-revid": "{{PLURAL:$1|En sidversion|$1 sidversioner}} kunde inte återställas, eftersom dess <code>rev_id</code> användes redan.",
        "undelete-nodiff": "Ingen tidigare version hittades.",
        "undeletebtn": "Återställ",
        "undeletelink": "visa/återställ",
        "undeletedrevisions": "{{PLURAL:$1|en version återställd|$1 versioner återställda}}",
        "undeletedrevisions-files": "$1 {{PLURAL:$1|version|versioner}} och $2 {{PLURAL:$2|fil|filer}} återställda",
        "undeletedfiles": "{{PLURAL:$1|en fil återställd|$1 filer återställda}}",
-       "cannotundelete": "Återställning misslyckades:\n$1",
+       "cannotundelete": "En del eller alla återställningar misslyckades:\n$1",
        "undeletedpage": "'''$1 har återställts'''\n\nSe [[Special:Log/delete|raderingsloggen]] för en förteckning över de senaste raderingarna och återställningarna.",
        "undelete-header": "Se [[Special:Log/delete|raderingsloggen]] för nyligen raderade sidor.",
        "undelete-search-title": "Sök efter raderade sidor",
        "sp-contributions-newbies-sub": "Från nya konton",
        "sp-contributions-newbies-title": "Bidrag från nya konton",
        "sp-contributions-blocklog": "blockeringslogg",
-       "sp-contributions-suppresslog": "undanhållna användarbidrag",
-       "sp-contributions-deleted": "raderade användarbidrag",
+       "sp-contributions-suppresslog": "censurerade {{GENDER:$1|användarbidrag}}",
+       "sp-contributions-deleted": "raderade {{GENDER:$1|användarbidrag}}",
        "sp-contributions-uploads": "uppladdningar",
        "sp-contributions-logs": "loggar",
        "sp-contributions-talk": "diskussion",
index 3f5bf22..3685734 100644 (file)
        "passwordreset-emailtext-ip": "Ftoś (cheba Ty, s IP $1)\npado, aże chce informacyji lo konta do {{GRAMMAR:MS.lp{{SITENAME}}}} ($4).\nZe tym ausdrukym sům powjůnzane kůnta:\n$2\n\n{{PLURAL:$3|Tymczasowygo hasła|Tymczasowych hasył}} możno użyć we {{PLURAL:$5|jedyn dźyń|$5 dńi}}.\n\nJak chćołżeś gynał to zrobjyć, to zaloguj śe terozki a podej swoje hasło.\n\nJak ftoś inkszy chćoł nowe hasło abo jak Ci śe przipůmńoło stare a ńy chcysz nowygo, to zignoruj to a używej starygo hasła.",
        "passwordreset-emailelement": "Mjano sprowjorza: \n$1\n\nTymczasowe hasło: \n$2",
        "passwordreset-emailsentemail": "E-brif posłany.",
-       "passwordreset-emailsent-capture": "E-brif posłony, kerego widać niżej.",
-       "passwordreset-emailerror-capture": "Ńy udoło śe posłać wjadomości lo {{GENDER:$2|używocza|używoczki}}: $1",
        "changeemail": "Pomjyno ausdruka e-mail",
        "changeemail-header": "Pomjyno ausduku e-mail",
        "changeemail-no-info": "Muśisz być zalogowany, coby uzyskać bezpostrzedńi dostymp do tyj zajty.",
        "undo-failure": "Sprowjyńo ńy idźe wycofać skuli kůnflikta ze wersyjůma postrzedńimi.",
        "undo-norev": "Sprowjyńo ńy idźe cofnůńć skuli tego, co ńy istńije abo uostoło wyćepane.",
        "undo-summary": "Wycůfańy wersyji $1 naszkryflanej bez [[Special:Contributions/$2|$2]] ([[User talk:$2|godka]])",
-       "cantcreateaccounttitle": "Ńy do śe utworzić kůnta",
        "cantcreateaccount-text": "Tworzyńy kůnta s tygo adresu IP ('''$1''') uostoło zawarte bez użytkowńika [[User:$3|$3]].\n\nSkuli: ''$2''",
        "viewpagelogs": "Uobocz rejery uoperacyji lo tyj zajty",
        "nohistory": "Ta zajta ńy mo swojij historyje sprowjyń.",
index ccd1f6c..f80b4cd 100644 (file)
        "passwordreset-emailelement": "பயனர் பெயர்:  \n$1\n\nதற்காலிகக் கடவுச்சொல்: \n$2",
        "passwordreset-emailsentemail": "இது உங்கள் கணக்கிற்கான பதிவு செய்யப்பட்ட மின்னஞ்சலாயின், கடவுச்சொல் மீட்டமைக்கும் மின்னஞ்சல் அனுப்பப்படும்",
        "passwordreset-emailsentusername": "இது உங்கள் கணக்கிற்கான பதிவு செய்யப்பட்ட மின்னஞ்சலாயின், கடவுச்சொல் மீட்டமைக்கும் மின்னஞ்சல் அனுப்பப்படும்",
-       "passwordreset-emailsent-capture": "கீழே காண்பிக்கப்பட்டுள்ளது போல் கடவுச்சொல் மீட்டமைக்கும் மின்னஞ்சல் அனுப்பப்பட்டது.",
-       "passwordreset-emailerror-capture": "கடவுச்சொல் மீட்டமைக்கும் மின்னஞ்சல்  உருவாக்கப்பட்டுவிட்டது, அது கீழே காட்டப்பட்டுள்ளது, ஆனால் {{GENDER:$2|user}} அனுப்புவது தோல்வியடைந்தது:$1",
        "changeemail": "மின்னஞ்சல் முகவரியை மாற்று / நீக்கு",
        "changeemail-header": "இந்த படிவத்தை உங்கள் மின்னஞ்சல் முகவரியை மாற்ற பூர்த்தி செய்யவும். நீங்கள் இந்த மாற்றத்தை உறுதிசெய்ய உங்கள் கடவுச்சொல்லை உள்ளிட வேண்டிவரும்.  உங்கள் கணக்கிலிருந்து ஏதாவது மின்னஞ்சலை நீக்க விரும்பினால், படிவத்தை சமர்ப்பிக்கும்போது மின்னஞ்சல் முகவரியை காலியாக விடவும்.",
-       "changeemail-passwordrequired": "இந்த மாற்றத்தை சேமிக்க உங்கள் கடவுச்சொல் தேவைப்படுகிறது.",
        "changeemail-no-info": "இப்பக்கத்தை நேரடியாக அணுகுவதற்கு நீங்கள் புகுபதிகை செய்திருக்கவேண்டும்.",
        "changeemail-oldemail": "தற்பொழுதுள்ள மின்னஞ்சல் முகவரி:",
        "changeemail-newemail": "புதிய மின்னஞ்சல் முகவரி:",
        "minoredit": "இது ஒரு சிறு தொகுப்பு",
        "watchthis": "இக்கட்டுரையைக் கவனிக்கவும்",
        "savearticle": "பக்கத்தைச் சேமி",
+       "publishpage": "பக்கத்தைப் பதிப்பிடுக",
+       "publishchanges": "மாற்றங்களைப் பதிப்பிடுக",
        "preview": "முன்தோற்றம்",
        "showpreview": "முன்தோற்றம் காட்டு",
        "showdiff": "மாற்றங்களைக் காட்டு",
        "undo-nochange": "திருத்தங்கள் ஏற்கனவே நீக்கப்பட்டதாக தோன்றுகிறது.",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|Talk]]) பயனரால் செய்யப்பட்ட திருத்தம் $1 இல்லாது செய்யப்பட்டது",
        "undo-summary-username-hidden": "மறை பயனரால் செய்யப்பட்ட மீள்பார்வை $1 ஐ நீக்கு",
-       "cantcreateaccounttitle": "கணக்கைத் தொடக்க முடியாது",
        "cantcreateaccount-text": "இந்த இணைய விதிமுறை இலக்க முகவரியிலிருந்து (IP address) ('''$1''') பயனர் கணக்குகள் தொடங்குவதை பயனர் [[User:$3|$3]] தடை செய்துள்ளார்.\n\nஇதற்காக $3 கொடுத்துள்ள காரணங்கள்  ''$2''",
        "cantcreateaccount-range-text": "இந்த இணைய விதிமுறை இலக்க முகவரி அளவில் உள்ள(IP address) <strong>$1</strong>,  உங்கள் முகவரி (<strong>$4</strong>) உட்பட, பயனர் கணக்குகள் தொடங்குவதை [[User:$3|$3]] தடை செய்துள்ளார்.\n\nஇதற்காக $3 கொடுத்துள்ள காரணங்கள் <em>$2</em>",
        "viewpagelogs": "இப்பக்கத்துக்கான பதிகைகளைப் பார்",
index 1ecf70c..8368ac5 100644 (file)
                        "వైజాసత్య",
                        "아라",
                        "Macofe",
-                       "Matma Rex"
+                       "Matma Rex",
+                       "WP MANIKHANTA"
                ]
        },
        "tog-underline": "లంకె క్రీగీత:",
        "tog-hideminor": "ఇటీవలి మార్పులలో చిన్న మార్పులను దాచు",
        "tog-hidepatrolled": "ఇటీవలి మార్పులలో నిఘా ఉన్న మార్పులను దాచు",
        "tog-newpageshidepatrolled": "కొత్త పేజీల జాబితా నుంచి నిఘా ఉన్న పేజీలను దాచు",
+       "tog-hidecategorization": "పేజీ వర్గీకరణను దాచు",
        "tog-extendwatchlist": "కేవలం ఇటీవలి మార్పులే కాక, మార్పులన్నీ చూపించటానికి నా వీక్షణా జాబితాను పెద్దది చేయి",
        "tog-usenewrc": "ఇటీవలి మార్పులు మరియు వీక్షణ జాబితాలలో మార్పులను పేజీ వారీగా చూపించు",
        "tog-numberheadings": "శీర్షికలకు అప్రమేయంగా వరుస సంఖ్యలు చేర్చు",
@@ -40,6 +42,7 @@
        "tog-watchdefault": "నేను మార్చే పేజీలను మరియు దస్త్రాలను నా వీక్షణ జాబితాకు చేర్చు",
        "tog-watchmoves": "నేను తరలించిన పేజీలను మరియు దస్త్రాలను నా వీక్షణ జాబితాకు చేర్చు",
        "tog-watchdeletion": "నేను తొలగించిన పేజీలను మరియు దస్త్రాలను నా వీక్షణ జాబితాకు చేర్చు",
+       "tog-watchuploads": "నేను ఎక్కించే కొత్త దస్త్రాలను నా వీక్షణ జాబితాకు చేర్చు",
        "tog-watchrollback": "నేను పునస్స్థాపించిన పేజీలను నా వీక్షణ జాబితాకు జోడించు",
        "tog-minordefault": "అప్రమేయంగా నా మార్పులను చిన్న మార్పులుగా గుర్తించు",
        "tog-previewontop": "వ్యాసం మార్పుల మునుచూపును ఎడిట్ పెట్టె పైన చూపు",
@@ -59,6 +62,7 @@
        "tog-watchlisthideliu": "లాగిన్ ఐన వాడుకరులు చేసే మార్పులను వీక్షణా జాబితాలో చూపించకు",
        "tog-watchlisthideanons": "అజ్ఞాత వాడుకరుల మార్పులను వీక్షణా జాబితాలో చూపించకు",
        "tog-watchlisthidepatrolled": "నిఘా ఉన్న మార్పులను వీక్షణజాబితా నుంచి దాచిపెట్టు",
+       "tog-watchlisthidecategorization": "పేజీ వర్గీకరణను దాచు",
        "tog-ccmeonemails": "నేను ఇతర వాడుకరులకు పంపించే ఈ-మెయిళ్ల కాపీలను నాకు కూడా పంపు",
        "tog-diffonly": "తేడాల కింద, పేజీలోని సమాచారాన్ని చూపించొద్దు",
        "tog-showhiddencats": "దాచిన వర్గాలను చూపించు",
        "protectedinterface": "ఈ పేజీ, ఈ వికీ యొక్క సాఫ్టువేరు ఇంటరుఫేసుకు చెందిన టెక్స్టును అందిస్తుంది. దుశ్చర్యల నివారణ కోసమై దీన్ని సంరక్షించాం. వికీలన్నిటిలోను అనువాదాలను చేర్చాలన్నా, మార్చాలన్నా మీడియావికీ స్థానికీకరణ ప్రాజెక్టైన [https://translatewiki.net/ translatewiki.net] ను వాడండి.",
        "editinginterface": "<strong>హెచ్చరిక:</strong> సాఫ్టువేరుకు ఇంటరుఫేసు టెక్స్టును అందించేందుకు పనికొచ్చే పేజీని మీరు సరిదిద్దుతున్నారు.\nఈ పేజీలో చేసే మార్పుల వల్ల ఇతర వాడుకరులకు ఇంటరుఫేసు కనబడే విధానంలో తేడావస్తుంది.",
        "translateinterface": "అన్ని వికీలలో కనిపించేలా అనువాదాలు చేర్చాలన్నా, మార్చాలన్నా, దయచేసి [https://translatewiki.net/ translatewiki.net] ను వాడండి. ఇది మీడియావికీ స్థానికీకరణ ప్రాజెక్టు.",
-       "cascadeprotected": "à°\95à°¿à°\82ది {{PLURAL:$1|à°ªà±\87à°\9cà±\80ని|à°ªà±\87à°\9cà±\80లనà±\81}} à°\95ాసà±\8dà°\95à±\87à°¡à°¿à°\82à°\97à±\81 à°\86à°ªà±\8dà°·à°¨à±\81à°¤à±\8b à°\9aà±\87సి à°¸à°\82à°°à°\95à±\8dà°·à°¿à°\82à°\9aారà±\81. à°ªà±\8dà°°à°¸à±\8dà°¤à±\81à°¤ à°ªà±\87à°\9cà±\80, à°\88 à°ªà±\87à°\9cà±\80à°²à±\8dà°²à±\8b à°\87à°\82à°\95à±\8dà°²à±\82à°¡à±\81 à°\85యి à°\89à°\82ది à°\95ాబà°\9fà±\8dà°\9fà°¿, à°¦à°¿à°¦à±\8dà°¦à±\81బాà°\9fà±\81 à°\9aà±\87à°¸à±\87 à°µà±\80à°²à±\81 à°²à±\87à°\95à±\81à°\82à°¡à°¾ à°\87ది à°\95à±\82à°¡à°¾ à°°à°\95à±\8dషణలà±\8b à°\89à°\82ది.\n$2",
+       "cascadeprotected": "à°\95à°¿à°\82ది {{PLURAL:$1|à°ªà±\87à°\9cà±\80ని|à°ªà±\87à°\9cà±\80లనà±\81}} à°\95ాసà±\8dà°\95à±\87à°¡à°¿à°\82à°\97à±\81 à°\86à°ªà±\8dà°·à°¨à±\81à°¤à±\8b à°¸à°\82à°°à°\95à±\8dà°·à°¿à°\82à°\9aబడిà°\82ది. à°ªà±\8dà°°à°¸à±\8dà°¤à±\81à°¤ à°ªà±\87à°\9cà±\80, à°\88 à°ªà±\87à°\9cà±\80à°²à±\8dà°²à±\8b à°\9fà±\8dరానà±\8dà°¸à±\8dâ\80\8cà°\95à±\8dà°²à±\82à°¡à±\81 à°\85యి à°\89à°\82ది à°\95ాబà°\9fà±\8dà°\9fà°¿, à°¦à°¿à°¦à±\8dà°¦à±\81బాà°\9fà±\81 à°\9aà±\87à°¸à±\87 à°µà±\80à°²à±\81 à°²à±\87à°\95à±\81à°\82à°¡à°¾ à°\87ది à°\95à±\82à°¡à°¾ à°°à°\95à±\8dషణలà±\8b à°\89à°\82ది:\n$2",
        "namespaceprotected": "'''$1''' నేంస్పేసులో మార్పులు చేయటానికి మీకు అనుమతి లేదు.",
        "customcssprotected": "ఈ CSS పేజీని మార్చేందుకు మీకు అనుమతి లేదు. ఎందుకంటే వేరే వాడుకరి యొక్క వ్యక్తిగత సెట్టింగులు అందులో ఉన్నాయి.",
        "customjsprotected": "ఈ JavaScript పేజీని మార్చేందుకు మీకు అనుమతి లేదు. ఎందుకంటే వేరే వాడుకరి యొక్క వ్యక్తిగత సెట్టింగులు అందులో ఉన్నాయి.",
        "virus-scanfailed": "స్కాన్ విఫలమైంది (సంకేతం $1)",
        "virus-unknownscanner": "అజ్ఞాత యాంటీవైరస్:",
        "logouttext": "<strong>ఇప్పుడు మీరు లాగౌటయ్యారు.</strong>\n\nఅయితే, ఓ గమనిక.. మీ విహారిణిలోని కోశాన్ని ఖాళీ చేసేవరకూ కొన్ని పేజీలు మీరింకా లాగినై ఉన్నట్లుగానే చూపించవచ్చు.",
+       "cannotlogoutnow-title": "ఇప్పుడు లాగౌట్ అవలేరు",
+       "cannotlogoutnow-text": "$1 ను వాడుతూండగా లాగౌట్ అవలేరు.",
        "welcomeuser": "స్వాగతం, $1!",
        "welcomecreation-msg": "మీ ఖాతాని సృష్టించాం.\nమీ [[Special:Preferences|{{SITENAME}} అభిరుచులను]] మార్చుకోవడం మరువకండి.\nతెలుగు వికీపీడియాలో తెలుగులోనే రాయాలి. వికీలో రచనలు చేసే ముందు, కింది సూచనలను గమనించండి.\nతెలుగు {{SITENAME}}లో తెలుగులోనే రాయాలి. వికీలో రచనలు చేసే ముందు, కింది సూచనలను గమనించండి.\n*వికీని త్వరగా అర్థం చేసుకునేందుకు [[వికీపీడియా:5 నిమిషాల్లో వికీ|5 నిమిషాల్లో వికీ]] పేజీని చూడండి.\n*తెలుగులో రాసేందుకు ఇంగ్లీషు అక్షరాల ఉచ్ఛారణతో తెలుగు టైపు చేసే [[వికీపీడియా:టైపింగు సహాయం| టైపింగ్  సహాయం]] వాడవచ్చు. మరిన్ని ఉపకరణాల కొరకు [[కీ బోర్డు]] మరియు   తెరపై తెలుగు సరిగా లేకపోతే[[వికీపీడియా:Setting up your browser for Indic scripts|ఈ పేజీ]]  చూడండి.",
        "yourname": "వాడుకరి పేరు:",
        "remembermypassword": "ఈ కంప్యూటరులో నా ప్రవేశాన్ని గుర్తుంచుకో (గరిష్ఠంగా $1 {{PLURAL:$1|రోజు|రోజుల}}కి)",
        "userlogin-remembermypassword": "నన్ను లాగిన్ చేసే ఉంచు",
        "userlogin-signwithsecure": "సురక్షిత కనెక్షను వాడు",
+       "cannotloginnow-title": "ఇప్పుడు లాగిన్ అవలేరు",
+       "cannotloginnow-text": "$1 ను వాడుతూండగా లాగౌట్ అవలేరు.",
        "yourdomainname": "మీ డోమైను",
        "password-change-forbidden": "ఈ వికీలో మీరు సంకేతపదాలను మార్చలేరు.",
        "externaldberror": "డేటాబేసు అధీకరణలో లోపం జరిగింది లేదా మీ బయటి ఖాతాను తాజాకరించడానికి మీకు అనుమతి లేదు.",
        "login": "లాగినవండి",
+       "login-security": "మీ ఐడీని ధ్రువపరచుకోండి",
        "nav-login-createaccount": "లాగినవండి / ఖాతాని సృష్టించుకోండి",
        "userlogin": "లాగినవండి / ఖాతాను సృష్టించుకోండి",
        "userloginnocreate": "లాగినవండి",
        "userlogin-resetpassword-link": "మీ సంకేతపదాన్ని మర్చిపోయారా?",
        "userlogin-helplink2": "లాగినవడంలో సహాయం",
        "userlogin-loggedin": "మీరు ఈసరికే {{GENDER:$1|$1}} గా లాగిన్ అయి ఉన్నారు.\nవేరే వాడుకరిగా లాగినయేందుకు కింది ఫారమును వాడండి.",
+       "userlogin-reauth": "మీరు {{GENDER:$1|$1}} అని నిర్ధారించుకునేందుకు మళ్ళీ లాగిన్ అవాలి.",
        "userlogin-createanother": "మరొక ఖాతాను సృష్టించండి",
        "createacct-emailrequired": "ఈమెయిలు చిరునామా",
        "createacct-emailoptional": "ఈమెయిలు చిరునామా (ఐచ్చికం)",
        "createacct-reason-ph": "మీరు మరో ఖాతాను ఎందుకు సృష్టించుకుంటున్నారు",
        "createacct-submit": "మీ ఖాతాను సృష్టించుకోండి",
        "createacct-another-submit": "ఖాతాను సృష్టించు",
+       "createacct-continue-submit": "ఖాతా సృష్టిని కొనసాగించండి",
+       "createacct-another-continue-submit": "ఖాతా సృష్టిని కొనసాగించండి",
        "createacct-benefit-heading": "{{SITENAME}}ను తయారుచేస్తున్నది మీలాంటి వారే.",
        "createacct-benefit-body1": "{{PLURAL:$1|మార్పు|మార్పులు}}",
        "createacct-benefit-body2": "{{PLURAL:$1|పేజీ|పేజీలు}}",
        "createacct-benefit-body3": "ఇటీవలి {{PLURAL:$1|సమర్పకుడు|సమర్పకులు}}",
        "badretype": "మీరు ఇచ్చిన రెండు సంకేతపదాలు ఒకదానితో మరొకటి సరిపోలడం లేదు.",
+       "usernameinprogress": "ఈ వాడుకరి పేరుతో ఖాతా సృష్టించుకోవడం పురోగతిలో ఉంది. కాస్త ఆగండి.",
        "userexists": "ఇచ్చిన వాడుకరిపేరు ఇప్పటికే వాడుకలో ఉంది.\nవేరే పేరును ఎంచుకోండి.",
        "loginerror": "లాగిన్ లోపం",
        "createacct-error": "ఖాతా సృష్టించడంలో లోపం",
        "nocookiesnew": "ఖాతాని సృష్టించాం, కానీ మీరు ఇంకా లోనికి ప్రవేశించలేదు.\nవాడుకరుల ప్రవేశానికి {{SITENAME}} కూకీలను వాడుతుంది.\nమీరు కూకీలని అచేతనం చేసివున్నారు.\nదయచేసి వాటిని చేతనంచేసి, మీ కొత్త వాడుకరి పేరు మరియు సంకేతపదాలతో లోనికి ప్రవేశించండి.",
        "nocookieslogin": "వాడుకరుల ప్రవేశానికై {{SITENAME}} కూకీలను వాడుతుంది.\nమీరు కుకీలని అచేతనం చేసివున్నారు.\nవాటిని చేతనంచేసి ప్రయత్నించండి.",
        "nocookiesfornew": "మూలాన్ని కనుక్కోలేకపోయాం కాబట్టి, ఈ వాడుకరి ఖాతాను సృష్టించలేకపోయాం.\nమీ కంప్యూటర్లో కూకీలు చేతనమై ఉన్నాయని నిశ్చయించుకొని, ఈ పేజీని తిరిగి లోడు చేసి, మళ్ళీ ప్రయత్నించండి.",
+       "createacct-loginerror": "ఖాతా విజయవంతంగా సృష్టించబడింది, కానీ ఆటోమాటిగ్గా లాగిన్ అవలేరు.  స్వయంగా మీరే [[Special:UserLogin|లాగినవండి]].",
        "noname": "మీరు సరైన వాడుకరి పేరు ఇవ్వలేదు.",
-       "loginsuccesstitle": "à°ªà±\8dà°°à°µà±\87à°¶à°\82 à°µà°¿à°\9cయవà°\82తమà±\88à°\82ది",
+       "loginsuccesstitle": "లాà°\97ినయà±\8dయారà±\81",
        "loginsuccess": "<strong>మీరు ఇప్పుడు {{SITENAME}}లోనికి \"$1\"గా ప్రవేశించారు.</strong>",
-       "nosuchuser": "\"$1\" à°\85à°¨à±\87 à°ªà±\87à°°à±\81à°¤à±\8b à°µà°¾à°¡à±\81à°\95à°°à±\81à°²à±\81 à°²à±\87à°°à±\81.\nవాడà±\81à°\95à°°à°¿ పేర్లు కేస్ సెన్సిటివ్.\nఅక్షరక్రమం సరిచూసుకోండి, లేదా [[Special:CreateAccount|కొత్త ఖాతా సృష్టించుకోండి]].",
+       "nosuchuser": "\"$1\" à°\85à°¨à±\87 à°ªà±\87à°°à±\81à°¤à±\8b à°µà°¾à°¡à±\81à°\95à°°à°¿ à°\8eవరà±\82 à°²à±\87à°°à±\81.\nవాడà±\81à°\95à°°à°¿పేర్లు కేస్ సెన్సిటివ్.\nఅక్షరక్రమం సరిచూసుకోండి, లేదా [[Special:CreateAccount|కొత్త ఖాతా సృష్టించుకోండి]].",
        "nosuchusershort": "\"$1\" పేరుతో వాడుకరి ఎవరూ లేరు. పేరు సరి చూసుకోండి.",
        "nouserspecified": "వాడుకరి పేరును తప్పనిసరిగా ఇవ్వాలి.",
        "login-userblocked": "ఈ వాడుకరిని నిరోధించారు. ప్రవేశానికి అనుమతి లేదు.",
        "wrongpasswordempty": "ఖాళీ సంకేతపదం ఇచ్చారు. మళ్ళీ ప్రయత్నించండి.",
        "passwordtooshort": "సంకేతపదం కనీసం {{PLURAL:$1|1 అక్షరం|$1 అక్షరాల}} నిడివి ఉండాలి.",
        "passwordtoolong": "సంకేతపదంలో {{PLURAL:$1|1 అక్షరం|$1 అక్షరాల}} కన్నా ఎక్కువ ఉండకూడదు.",
+       "passwordtoopopular": "మామూలుగా వాడే సంకేతపదాలను వాడే వీల్లేదు. మరింత విశిష్టమైన సంకేతపదాన్ని ఎంచుకోండి.",
        "password-name-match": "మీ సంకేతపదం మీ వాడుకరిపేరుకి భిన్నంగా ఉండాలి.",
        "password-login-forbidden": "ఈ వాడుకరిపేరు మరియు సంకేతపదాలను ఉపయోగించడం నిషిద్ధం.",
        "mailmypassword": "సంకేతపదాన్ని మార్చు",
        "noemail": "వాడుకరి \"$1\" కు ఈమెయిలు చిరునామా నమోదయి లేదు.",
        "noemailcreate": "మీరు సరైన ఈమెయిల్ చిరునామాని ఇవ్వాలి",
        "passwordsent": "\"$1\" కొరకు నమోదైన ఈ-మెయిలు చిరునామాకి కొత్త సంకేతపదాన్ని పంపించాం.\nఅది అందిన తర్వాత ప్రవేశించి చూడండి.",
-       "blocked-mailpassword": "దిదà±\8dà°¦à±\81బాà°\9fà±\8dà°²à±\81 à°\9aà±\86à°¯à±\8dà°¯à°\95à±\81à°\82à°¡à°¾ à°®à±\80 à°\90à°ªà±\80à°\85à°¡à±\8dà°°à°¸à±\81à°¨à±\81 à°¨à°¿à°°à±\8bధిà°\82à°\9aà°¾à°\82. à°\85à°\82à°\9aà±\87à°¤, à°¦à±\81à°¶à±\8dà°\9aà°°à±\8dయల à°¨à°¿à°µà°¾à°°à°£ à°\95à±\8bà°¸à°\82 à°\97ానà±\81, à°®à°°à°\9aà°¿à°ªà±\8bయిన à°¸à°\82à°\95à±\87తపదానà±\8dని à°ªà±\8aà°\82à°¦à±\87 à°µà±\80à°²à±\81 à°\88 à°\90à°ªà±\80à°\95à°¿ à°²à±\87à°¦à±\81.",
+       "blocked-mailpassword": "దిద్దుబాట్లు చెయ్యకుండా మీ ఐపీఅడ్రసును నిరోధించాం. దుశ్చర్యల నివారణ కోసం గాను, మరచిపోయిన సంకేతపదాన్ని పొందే వీలు ఈ ఐపీకి లేదు.",
        "eauthentsent": "ఇచ్చిన ఈ-మెయిలు అడ్రసుకు ధృవీకరణ మెయిలు పంపించాం.\nఇకపై మేము ఆ ఖాతాకు మెయిలు పంపాలంటే, ముందుగా మీరు ఆ మెయిల్లో సూచించినట్లుగా చేసి, ఈ చిరునామా మీదేనని ధృవీకరించాలి.",
        "throttled-mailpassword": "గడచిన {{PLURAL:$1|ఒక గంటలో|$1 గంటల్లో}} సంకేతపదం మార్చినట్లుగా ఒక మెయిలు పంపించివున్నాం.\nదుశ్చర్యలను నివారించేందుకు గాను, {{PLURAL:$1|ఒక గంటకు|$1 గంటలకు}} ఒక్కసారి మాత్రమే సంకేతపదం మార్పు మెయిలు పంపిస్తాము.",
        "mailerror": "మెయిలు పంపించడంలో లోపం: $1",
        "createacct-another-realname-tip": "అసలు పేరు ఐచ్ఛికం.\nమీరు దాన్ని ఇస్తే, వాడుకరి పనుల శ్రేయస్సు ఆ పేరుకు ఆపాదించబడుతుంది.",
        "pt-login": "లాగినవండి",
        "pt-login-button": "లాగినవండి",
+       "pt-login-continue-button": "లాగిన్ అవడాన్ని కొనసాగించండి",
        "pt-createaccount": "ఖాతా సృష్టించుకోండి",
        "pt-userlogout": "లాగౌటవండి",
        "php-mail-error-unknown": "PHP యొక్క mail() ఫంక్షన్‍లో ఏదో తెలియని లోపం దొర్లింది",
        "newpassword": "కొత్త సంకేతపదం:",
        "retypenew": "సంకేతపదం, మళ్ళీ",
        "resetpass_submit": "సంకేతపదాన్ని మార్చి లాగినవండి",
-       "changepassword-success": "à°®à±\80 à°¸à°\82à°\95à±\87తపదà°\82 à°µà°¿à°\9cయవà°\82à°¤à°\82à°\97à°¾ à°®à°¾à°°à±\8dà°\9aబడిà°\82ది.",
+       "changepassword-success": "à°®à±\80 à°¸à°\82à°\95à±\87తపదà°\82 à°®à°¾à°°à±\8dà°\9aబడిà°\82ది!",
        "changepassword-throttled": "కొద్దిసేపటిగా మీరు చాలా లాగిన్ ప్రయత్నాలు చేసారు.\nమళ్ళీ ప్రయత్నించే ముందు $1 ఆగండి.",
+       "botpasswords-label-appid": "బాట్ పేరు:",
+       "botpasswords-label-create": "సృష్టించు",
+       "botpasswords-label-update": "తాజాకరించు",
+       "botpasswords-label-cancel": "రద్దుచేయి",
+       "botpasswords-label-delete": "తొలగించు",
+       "botpasswords-label-resetpassword": "సంకేతపదాన్ని మార్చు",
+       "botpasswords-label-grants": "వర్తించే గ్రాంట్లు:",
+       "botpasswords-label-restrictions": "వాడుక పరిమితులు:",
+       "botpasswords-label-grants-column": "గ్రాంటు చేసాం",
+       "botpasswords-bad-appid": "బాట్ పేరు \"$1\" సరైనది కాదు.",
+       "botpasswords-insert-failed": "బాట్ పేరు \"$1\"ను చేర్చలేకపోయాం. దీన్ని ఇంతకు ముందే చేర్చారా ఏంటి?",
+       "botpasswords-update-failed": "బాట్ పేరు \"$1\" ను తాజాకరించలేకపోయాం. దీన్ని తొలగించారా?",
+       "botpasswords-created-title": "బాట్ సంకేతపదాన్ని సృష్టించాం",
+       "botpasswords-created-body": "వాడుకరి \"$2\" కు చెందిన \"$1\" అనే బాట్‌కు బాట్ సంకేతపదాన్ని సృష్టించాం.",
+       "botpasswords-updated-title": "బాట్ సంకేతపదాన్ని తాజాకరించాం",
+       "botpasswords-updated-body": "వాడుకరి \"$2\" కు చెందిన \"$1\" అనే బాట్‌ యొక్క బాట్ సంకేతపదాన్ని తాజాకరించాం.",
+       "botpasswords-deleted-title": "బాట్ సంకేతపదాన్ని తొలగించాం",
+       "botpasswords-deleted-body": "వాడుకరి \"$2\" కు చెందిన \"$1\" అనే బాట్‌ యొక్క బాట్ సంకేతపదాన్ని తొలగించాం.",
+       "botpasswords-newpassword": "<strong>$1</strong> తో లాగినయేందుకు కొత్త సంకేతపదం <strong>$2</strong>. <em>భావి ఉపయోగం కోసం దీన్ని జాగ్రత్త చేసుకోండి.</em>",
+       "botpasswords-not-exist": "వాడుకరి \"$1\" కి \"$2\" అనే బాట్ సంకేతపదం లేదు.",
        "resetpass_forbidden": "సంకేతపదాలను మార్చటం కుదరదు",
+       "resetpass_forbidden-reason": "సంకేతపదాలు మార్చజాలరు: $1",
        "resetpass-no-info": "ఈ పేజీని నేరుగా చూడటానికి మీరు లాగినయి వుండాలి.",
        "resetpass-submit-loggedin": "సంకేతపదాన్ని మార్చు",
        "resetpass-submit-cancel": "రద్దుచేయి",
-       "resetpass-wrong-oldpass": "తపà±\8dà°ªà±\81à°¡à±\81 à°¤à°¾à°¤à±\8dà°\95ాలిà°\95 à°²à±\87దా à°ªà±\8dà°°à°¸à±\8dà°¤à±\81à°¤ à°¸à°\82à°\95à±\87తపదà°\82.\nà°®à±\80à°°à±\81 à°®à±\80 à°¸à°\82à°\95à±\87తపదానà±\8dని à°\87à°ªà±\8dà°ªà°\9fà°¿à°\95à±\87 à°µà°¿à°\9cయవà°\82à°¤à°\82à°\97à°¾ à°®à°¾à°°à±\8dà°\9aà±\81à°\95à±\8aనివà±\81à°\82à°¡à°µà°\9aà±\8dà°\9aà±\81 à°²à±\87దా à°\95à±\8aà°¤à±\8dà°¤ à°¤à°¾à°¤à±\8dà°\95ాలిà°\95 à°¸à°\82à°\95à±\87తపదà°\82 à°\95à±\8bà°¸à°\82 à°\85à°­à±\8dయరà±\8dథిà°\82à°\9aారు.",
+       "resetpass-wrong-oldpass": "తపà±\8dà°ªà±\81à°¡à±\81 à°¤à°¾à°¤à±\8dà°\95ాలిà°\95 à°²à±\87దా à°ªà±\8dà°°à°¸à±\8dà°¤à±\81à°¤ à°¸à°\82à°\95à±\87తపదà°\82.\nà°®à±\80à°°à±\81 à°®à±\80 à°¸à°\82à°\95à±\87తపదానà±\8dని à°\87à°ªà±\8dà°ªà°\9fà°¿à°\95à±\87 à°®à°¾à°°à±\8dà°\9aà±\81à°\95à±\8aని à°\89à°\82à°¡à°µà°\9aà±\8dà°\9aà±\81 à°²à±\87దా à°\95à±\8aà°¤à±\8dà°¤ à°¤à°¾à°¤à±\8dà°\95ాలిà°\95 à°¸à°\82à°\95à±\87తపదà°\82 à°\95à±\8bà°¸à°\82 à°\85à°­à±\8dయరà±\8dథిà°\82à°\9aà°¿ à°\89à°\82à°¡à°µà°\9aà±\8dà°\9aు.",
        "resetpass-recycled": "మీ ప్రస్తుత సంకేతపదాన్ని వేరే సంకేతపదంతో మార్చుకోండి",
        "resetpass-temp-emailed": "మీరు మీ ఈమెయిలుకు పంపించిన తాత్కాలిక కోడుతో లాగినయ్యారు. లాగిన్ను పూర్తి చేసేందుకు, ఇక్కడ మీరు తప్పనిసరిగా సంకేతపదం మార్చుకోవాలి:",
        "resetpass-temp-password": "తాత్కాలిక సంకేతపదం:",
        "passwordreset-emailtext-ip": "ఎవరో (బహుశా మీరే, ఐపీ అడ్రసు $1 నుంచి)  {{SITENAME}} ($4) లో మీ సంకేతపదాన్ని మార్చమంటూ అడిగారు. కింది వాడుకరి {{PLURAL:$3|ఖాతా|ఖాతాలు}}\nఈ ఈమెయిలు చిరునామాతో అనుసంధింపబడి ఉన్నాయి:\n\n$2\n\n{{PLURAL:$3|ఈ సంకేతపదానికి|ఈ సంకేతపదాలకు}} {{PLURAL:$5|ఒక్కరోజులో|$5 రోజుల్లో}} కాలం చెల్లుతుంది.\nఇప్పుడు మీరు లాగినై కొత్త సంకేతపదాన్ని ఎంచుకోవాల్సి ఉంటుంది. ఈ అభ్యర్ధన చేసింది మరెవరైనా అయినా, లేక మీ అసలు సంకేతపదం మీకు గుర్తొచ్చి దాన్ని మార్చాల్సిన అవసరం లేదని అనుకున్నా, మీరీ సందేశాన్ని పట్టించుకోనక్కర్లేదు. పాత సంకేతపదాన్నే వాడుకోవచ్చు.",
        "passwordreset-emailtext-user": "{{SITENAME}} లోని వాడుకరి $1, {{SITENAME}} ($4) లోని మీ సంకేతపదాన్ని మార్చమంటూ అడిగారు. కింది వాడుకరి {{PLURAL:$3|ఖాతా|ఖాతాలు}}\nఈ ఈమెయిలు అడ్రసుతో అనుసంధింపబడి ఉన్నాయి:\n\n$2\n\n{{PLURAL:$3|ఈ తాత్కాలిక సంకేతపదానికి|ఈ తాత్కాలిక సంకేతపదాలకు}} {{PLURAL:$5|ఒక్క రోజులో|$5 రోజుల్లో}} కాలం చెల్లుతుంది.\nఇప్పుడు మీరు లాగినై కొత్త సంకేతపదాన్ని ఎంచుకోవాల్సి ఉంటుంది. ఈ అభ్యర్ధన చేసింది మరెవరైనా అయినా, లేక మీ అసలు సంకేతపదం మీకు గుర్తొచ్చి దాన్ని మార్చాల్సిన అవసరం లేదని అనుకున్నా, మీరీ సందేశాన్ని పట్టించుకోనక్కర్లేదు. పాత సంకేతపదాన్నే వాడుకోవచ్చు.",
        "passwordreset-emailelement": "వాడుకరిపేరు: \n$1\n\nతాత్కాలిక సంకేతపదం: \n$2",
-       "passwordreset-emailsentemail": "సంకేతపదం మార్పు ఈమెయిలును పంపించాం.",
-       "passwordreset-emailsent-capture": "క్రింద చూపిన సంకేతపదం మార్పు ఈమెయిలును పంపించాం.",
-       "passwordreset-emailerror-capture": "కింద చూపిన సంకేతపదం మార్పు ఈమెయిలును తయారుచేసాం. కానీ దాన్ని {{GENDER:$2|వాడుకరికి}} పంపడం విఫలమైంది: $1",
-       "changeemail": "ఈ-మెయిలు చిరునామా మార్పు",
-       "changeemail-header": "ఖాతా ఈ-మెయిల్ చిరునామాని మార్చండి",
+       "passwordreset-emailsentemail": "ఈ ఈమెయిలు చిరునామా మీ ఖాతాకు అనుసంధించి ఉంటే, సంకేతపదం మార్పు ఈమెయిలు పంపించబడుతుంది.",
+       "passwordreset-emailsentusername": "ఈ వాడుకరిపేరుకు ఏదైనా ఈమెయిలు చిరునామా అనుసంధించి ఉంటే, సంకేతపదం మార్పు ఈమెయిలు పంపించబడుతుంది.",
+       "passwordreset-emailsent-capture2": "సంకేతపదం మార్పు {{PLURAL:$1|ఈమెయిలును|ఈమెయిళ్ళను}} పంపించాం. {{PLURAL:$1|వాడుకరిపేరు, సంకేతపదాన్ని|వాడుకరిపేర్లు, సంకేతపదాల జాబితాను}} కింద చూపించాం.",
+       "passwordreset-emailerror-capture2": "{{GENDER:$2|వాడుకరికి}} ఈమెయిలు పంపడం విఫలమైంది: $1 {{PLURAL:$3|వాడుకరిపేరు, సంకేతపదాన్ని|వాడుకరిపేర్లు, సంకేతపదాల జాబితాను}} కింద చూపించాం.",
+       "passwordreset-invalideamil": "తప్పు ఈ-మెయిలు చిరునామా",
+       "passwordreset-nodata": "వాడుకరిపేరుగానీ, ఈ-మెయిలు చిరునామా గానీ ఇవ్వలేదు",
+       "changeemail": "ఈ-మెయిలు చిరునామా మార్పు లేదా తొలగింపు",
+       "changeemail-header": "మీ ఈ-మెయిల్ చిరునామాను మార్చుకునేందుకు ఈ ఫారమును నింపండి. అసలు మీ ఖాతాకు ఈ-మెయిలు చిరునామా దేన్నీ జోడించ వద్దనుకుంటే, కొత్త ఈ-మెయిలు చిరునామాను ఖాళీగా ఉంచి, ఫారాన్ని సమర్పించండి.",
        "changeemail-no-info": "ఈ పేజీని నేరుగా చూడటానికి మీరు లాగినయి వుండాలి.",
        "changeemail-oldemail": "ప్రస్తుత ఈ-మెయిలు చిరునామా:",
        "changeemail-newemail": "కొత్త ఈ-మెయిలు చిరునామా:",
+       "changeemail-newemail-help": "ఈ-మెయిలు చిరునామాను తొలగించాం.",
        "changeemail-none": "(ఏమీలేదు)",
        "changeemail-password": "మీ {{SITENAME}} సంకేతపదం:",
        "changeemail-submit": "ఈ-మెయిల్ మార్చు",
        "changeemail-throttled": "మరీ ఎక్కువగా లాగిన్ ప్రయత్నాలు చేసారు.\nమళ్ళీ ప్రయత్నించే ముందు $1 ఆగండి.",
+       "changeemail-nochange": "వేరే ఈ-మెయిలు చిరునామా ఇవ్వండి.",
        "resettokens": "టోకెన్ ను రీసెట్ చెయ్యి",
        "resettokens-text": "మీ ఖాతాకు అనుబంధంగా ఉన్న గోపనీయ డేటాను చూపించే టోకెన్లను మీరు ఇక్కడ రీసెట్ చెయ్యవచ్చు.\n\nమీరా టోకెన్లను పొరపాటున ఎవరికైనా ఇచ్చి ఉన్నా, లేక మీ ఖాతా వివరాలు మరెవరికైనా తెలిసిపోయినా మీరీ పని చెయ్యాలి.",
        "resettokens-no-tokens": "రీసెట్ చేసేందుకు టోకెన్లేమీ లేవు.",
        "minoredit": "ఇది ఒక చిన్న మార్పు",
        "watchthis": "ఈ పుట మీద కన్నేసి ఉంచు",
        "savearticle": "పేజీని భద్రపరచు",
+       "savechanges": "మార్పులను భద్రపరచు",
+       "publishpage": "పేజీని ప్రచురించు",
+       "publishchanges": "మార్పులను ప్రచురించు",
        "preview": "మునుజూపు",
        "showpreview": "మునుజూపు చూపు",
        "showdiff": "తేడాలను చూపించు",
        "missingsummary": "<strong>గుర్తు చేస్తున్నాం:</strong> మీరు దిద్దుబాటు సారాంశమేమీ ఇవ్వలేదు. పేజీని మళ్ళీ భద్రపరచమని చెబితే సారాంశమేమీ లేకుండానే దిద్దుబాటును భద్రపరుస్తాం.",
        "selfredirect": "<strong>హెచ్చరిక:</strong> మీరు ఈ పేజీని దానికే దారిమార్పు చేస్తున్నారు. బహుశా మీరు తప్పు దారిమార్పును సూచించి ఉండవచ్చు, లేదా మీరు తప్పుడు పేజీని మారుస్తున్నారు. \nమీరు \"{{int:savearticle}}\" ను నొక్కితే దారిమార్పు పేజీ ఖచ్చితంగా సృష్టించబడుతుంది.",
        "missingcommenttext": "కింద ఓ వ్యాఖ్య రాయండి.",
-       "missingcommentheader": "<strong>గుర్తు చేస్తున్నాం:</strong> ఈ వ్యాఖ్యకు మీరు విషయం/శీర్షిక పెట్టలేదు.\n\"{{int:savearticle}}\"ని మళ్ళీ నొక్కితే, అది లేకుండానే మీ మార్పును భద్రపరుస్తాం.",
+       "missingcommentheader": "<strong>గుర్తు చేస్తున్నాం:</strong> ఈ వ్యాఖ్యకు మీరు విషయం పెట్టలేదు.\n\"{{int:savearticle}}\"ని మళ్ళీ నొక్కితే, అది లేకుండానే మీ మార్పును భద్రపరుస్తాం.",
        "summary-preview": "సారాంశం మునుజూపు:",
        "subject-preview": "విషయపు మునుజూపు:",
        "previewerrortext": "మీ మార్పులు మునుజూపు చూడటంలో తప్పిదమయింది.",
        "accmailtext": "[[User talk:$1|$1]] కొరకు ఒక యాదృచ్ఛిక సంకేతపదాన్ని $2కి పంపించాం. లాగినయ్యాక, ''[[Special:ChangePassword|సంకేతపదాన్ని మార్చుకోండి]]'' అనే పేజీలో ఈ సంకేతపదాన్ని మార్చుకోవచ్చు.",
        "newarticle": "(కొత్తది)",
        "newarticletext": "ఈ లింకుకు సంబంధించిన పేజీ లేనే లేదు.\nకింది పెట్టెలో మీ రచనను టైపు చేసి ఆ పేజీని సృష్టించండి (దీనిపై సమాచారం కొరకు [$1 సహాయం పేజీ] చూడండి). మీరిక్కడికి పొరపాటున వచ్చి ఉంటే, మీ బ్రౌజరు <strong>back</strong> మీట నొక్కండి.",
-       "anontalkpagetext": "----\n<em>à°\87ది à°\92à°\95 à°\85à°\9cà±\8dà°\9eాత à°µà°¾à°¡à±\81à°\95à°°à°¿ à°\9aà°°à±\8dà°\9aà°¾ à°ªà±\87à°\9cà±\80. à°\86 à°µà°¾à°¡à±\81à°\95à°°à°¿ à°\87à°\82à°\95à°¾ à°¤à°¨à°\95à±\88 à°\96ాతానà±\81 à°¸à±\83à°·à±\8dà°\9fà°¿à°\82à°\9aà±\81à°\95à±\8bà°²à±\87à°¦à±\81, à°²à±\87దా à°\96ాతా à°\89à°¨à±\8dనా à°¦à°¾à°¨à°¿à°¨à°¿ à°\89పయà±\8bà°\97à°¿à°\82à°\9aà°¡à°\82 à°²à±\87à°¦à±\81.</em>\nà°\85à°\82à°\9aà±\87à°¤, à°\85తణà±\8dణి/à°\86à°®à±\86à°¨à±\81 à°\97à±\81à°°à±\8dతిà°\82à°\9aడానిà°\95à°¿ à°\90.à°ªà±\80. à°\9aà°¿à°°à±\81నామానà±\81 à°µà°¾à°¡à°¾à°²à±\8dసి à°µà°\9aà±\8dà°\9aà°¿à°\82ది. \nà°\92à°\95à±\87 à°\90.à°ªà±\80. à°\9aà°¿à°°à±\81నామాని చాలా మంది వాడుకరులు ఉపయోగించే అవకాశం ఉంది. \nమీరూ అజ్ఞాత వాడుకరి అయితే, మీకు సంబంధంలేని వ్యాఖ్యలు మిమ్మల్ని ఉద్దేశించినట్టుగా అనిపిస్తే, భవిష్యత్తులో ఇతర అజ్ఞాత వాడుకరులతో అయోమయం లేకుండా ఉండటానికి, [[Special:CreateAccount|ఖాతాను సృష్టించుకోండి]] లేదా [[Special:UserLogin|లాగినవండి]].''",
+       "anontalkpagetext": "----\n<em>à°\87ది à°\92à°\95 à°\85à°\9cà±\8dà°\9eాత à°µà°¾à°¡à±\81à°\95à°°à°¿ à°\9aà°°à±\8dà°\9aà°¾ à°ªà±\87à°\9cà±\80. à°\86 à°µà°¾à°¡à±\81à°\95à°°à°¿ à°\87à°\82à°\95à°¾ à°¤à°¨à°\95à±\88 à°\96ాతానà±\81 à°¸à±\83à°·à±\8dà°\9fà°¿à°\82à°\9aà±\81à°\95à±\8bà°²à±\87à°¦à±\81, à°²à±\87దా à°\96ాతా à°\89à°¨à±\8dనా à°¦à°¾à°¨à°¿à°¨à°¿ à°\89పయà±\8bà°\97à°¿à°\82à°\9aà°¡à°\82 à°²à±\87à°¦à±\81.</em>\nà°\85à°\82à°\9aà±\87à°¤, à°\85తణà±\8dణి/à°\86à°®à±\86à°¨à±\81 à°\97à±\81à°°à±\8dతిà°\82à°\9aడానిà°\95à°¿ à°\90.à°ªà±\80. à°\9aà°¿à°°à±\81నామానà±\81 à°µà°¾à°¡à°¾à°²à±\8dసి à°µà°\9aà±\8dà°\9aà°¿à°\82ది. \nà°\86 à°\90.à°ªà±\80. à°\9aà°¿à°°à±\81నామానà±\81 చాలా మంది వాడుకరులు ఉపయోగించే అవకాశం ఉంది. \nమీరూ అజ్ఞాత వాడుకరి అయితే, మీకు సంబంధంలేని వ్యాఖ్యలు మిమ్మల్ని ఉద్దేశించినట్టుగా అనిపిస్తే, భవిష్యత్తులో ఇతర అజ్ఞాత వాడుకరులతో అయోమయం లేకుండా ఉండటానికి, [[Special:CreateAccount|ఖాతాను సృష్టించుకోండి]] లేదా [[Special:UserLogin|లాగినవండి]].''",
        "noarticletext": "ప్రస్తుతం ఈ పేజీలో పాఠ్యమేమీ లేదు.\nవేరే పేజీలలో [[Special:Search/{{PAGENAME}}|ఈ పేజీ శీర్షిక కోసం వెతకవచ్చు]],\n<span class=\"plainlinks\">[{{fullurl:{{#Special:Log}}|page={{FULLPAGENAMEE}}}} సంబంధిత చిట్టాలు చూడవచ్చు],\nలేదా [{{fullurl:{{FULLPAGENAME}}|action=edit}} ఈ పేజీని మార్చవచ్చు]</span>.",
        "noarticletext-nopermission": "ప్రస్తుతం ఈ పేజీలో పాఠ్యమేమీ లేదు.\nమీరు ఇతర పేజీలలో [[Special:Search/{{PAGENAME}}|ఈ పేజీ శీర్షిక కోసం వెతకవచ్చు]], లేదా <span class=\"plainlinks\">[{{fullurl:{{#Special:Log}}|page={{FULLPAGENAMEE}}}} సంబంధిత చిట్టాలలో వెతకవచ్చు]</span>, కానీ ఈ పేజీని సృష్టించడానికి మీకు అనుమతి లేదు.",
        "missing-revision": "\"{{FULLPAGENAME}}\" అనే పేజీ యొక్క కూర్పు #$1 ఉనికిలో లేదు. సాధారణంగా ఏదైనా తొలగించబడిన పేజీ యొక్క కాలం చెల్లిన చరితం లింకును నొక్కినపుడు ఇది జరుగుతుంది. వివరాలు [{{fullurl:{{#Special:Log}}/delete|page={{FULLPAGENAMEE}}}} తొలగింపు లాగ్] లో దొరుకుతాయి.",
        "previewnote": "<strong>ఇది మునుజూపు మాత్రమేనని గుర్తుంచుకోండి.</strong>\nమీ మార్పులు ఇంకా భద్రమవ్వలేదు!",
        "continue-editing": "సరిదిద్దే చోటుకి వెళ్ళండి",
        "previewconflict": "భద్రపరచిన తరువాత పై టెక్స్ట్‌ ఏరియాలోని టెక్స్టు ఇలాగ కనిపిస్తుంది.",
-       "session_fail_preview": "<strong>క్షమించండి! సెషను డేటా పోవడం వలన మీ మార్పులను స్వీకరించలేకపోతున్నాం.</strong>\nమళ్ళీ ప్రయత్నించండి.\nఅయినా పని జరక్కపోతే, ఓసారి [[Special:UserLogout|లాగౌటై]] మళ్ళీ లాగినయి ప్రయత్నించండి.",
-       "session_fail_preview_html": "<strong>సారీ! సెషను డేటా పోవడం వలన మీ దిద్దుబాటును ప్రాసెస్ చెయ్యలేలేక పోతున్నాం.</strong>\n\n''{{SITENAME}}లో ముడి HTML సశక్తమై ఉంది కాబట్టి, జావాస్క్రిప్టు దాడుల నుండి రక్షణగా మునుజూపును దాచేశాం.''\n\n<strong>మీరు చేసినది సరైన దిద్దుబాటే అయితే, మళ్ళీ ప్రయత్నించండి. అయినా పనిచెయ్యకపోతే, ఓ సారి [[Special:UserLogout|లాగౌటై]], మళ్ళీ లాగినయి చూడండి.</strong>",
+       "session_fail_preview": "సారీ! సెషను డేటా పోవడం వలన మీ మార్పులను ప్రాసెస్ చెయ్యలేకపోయాం.\n\nబహుశా మీరు లాగౌటయ్యారేమో. <strong>లాగినయ్యే ఉన్నారని నిర్ధారించుకుని, మళ్ళీ ప్రయత్నించండి.</strong> అయినా పని చెయ్యకపోతే, ఓసారి [[Special:UserLogout|లాగౌటై]], మళ్ళీ లాగినయి ప్రయత్నించండి. మీ బ్రౌజరు ఈ సైటు యొక్క కూకీలను అనుమతిస్తుందని కూడా నిర్ధారించుకోండి.",
+       "session_fail_preview_html": "<strong>సారీ! సెషను డేటా పోవడం వలన మీ దిద్దుబాటును ప్రాసెస్ చెయ్యలేలేక పోతున్నాం.</strong>\n\n<em>{{SITENAME}}లో ముడి HTML సశక్తమై ఉంది కాబట్టి, జావాస్క్రిప్టు దాడుల నుండి రక్షణగా మునుజూపును దాచేశాం.</em>\n\n<strong>మీరు చేసినది సరైన దిద్దుబాటే అయితే, మళ్ళీ ప్రయత్నించండి.</strong> అయినా పనిచెయ్యకపోతే, ఓ సారి [[Special:UserLogout|లాగౌటై]], మళ్ళీ లాగినయి చూడండి. మీ బ్రౌజరు ఈ సైటు యొక్క కూకీలను అనుమతిస్తుందని కూడా నిర్ధారించుకోండి.",
        "token_suffix_mismatch": "'''మీ క్లయంటు, దిద్దుబాటు టోకెన్‌లోని వ్యాకరణ గుర్తులను గజిబిజి చేసింది కాబట్టి మీ దిద్దుబాటును తిరస్కరించాం. పేజీలోని పాఠ్యాన్ని చెడగొట్టకుండా ఉండేందుకు గాను, ఆ దిద్దుబాటును రద్దు చేశాం. వెబ్‌లో ఉండే లోపభూయిష్టమైన అజ్ఞాత ప్రాక్సీ సర్వీసులను వాడినపుడు ఒక్కోసారి ఇలా జరుగుతుంది.'''",
        "edit_form_incomplete": "’’’ఈ ఎడిట్ ఫారంలోని కొన్ని భాగాలు సర్వరును చేరలేదు; మీ మార్పుచేర్పులు భద్రంగా ఉన్నాయని ధృవపరచుకుని, మళ్ళీ ప్రయత్నించండి.’’’",
        "editing": "$1 ని సవరిస్తున్నారు",
        "undo-nochange": "ఆ మార్పును ఈసరికే రద్దు చేసినట్లుగా కనిపిస్తోంది.",
        "undo-summary": "[[Special:Contributions/$2|$2]] ([[User talk:$2|చర్చ]]) యొక్క కూర్పు $1 ను రద్దుచెయ్యి",
        "undo-summary-username-hidden": "దాచబడిన వాడుకరి చేసిన కూర్పు $1 ని వెనక్కి తిప్పండి",
-       "cantcreateaccounttitle": "ఈ ఖాతా తెరవలేము",
        "cantcreateaccount-text": "ఈ ఐపీ అడ్రసు ('''$1''') నుండి ఖాతా సృష్టించడాన్ని [[User:$3|$3]] నిరోధించారు.\n\n$3 చెప్పిన కారణం: ''$2''",
        "cantcreateaccount-range-text": "<strong>$1</strong> శ్రేణిలోని IP చిరునామాల నుండి ఖాతా సృష్టించడాన్ని [[User:$3|$3]] నిషేధించారు. మీ IP చిరునామా (<strong>$4</strong>) ఈ శ్రేణిలోనే ఉంది.\n\n$3 ఇచ్చిన కారణం: <em>$2</em>",
        "viewpagelogs": "ఈ పేజీకి సంబంధించిన లాగ్‌లను చూడండి",
        "rightslogtext": "ఇది వాడుకరుల హక్కులకు జరిగిన మార్పుల చిట్టా.",
        "action-read": "ఈ పేజీని చదివే",
        "action-edit": "ఈ పేజీని సవరించే",
-       "action-createpage": "à°ªà±\87à°\9cà±\80లనà±\81 సృష్టించే",
-       "action-createtalk": "à°\9aà°°à±\8dà°\9aాపà±\87à°\9cà±\80లనà±\81 సృష్టించే",
+       "action-createpage": "à°\88 à°ªà±\87à°\9cà±\80ని సృష్టించే",
+       "action-createtalk": "à°\88 à°\9aà°°à±\8dà°\9aాపà±\87à°\9cà±\80ని సృష్టించే",
        "action-createaccount": "ఈ వాడుకరి ఖాతాని సృష్టించే",
        "action-history": "ఈ పేజీ యొక్క చరిత్రని చూడండి",
        "action-minoredit": "ఈ మార్పుని చిన్నదిగా గుర్తించే",
        "action-viewmyprivateinfo": "మీ గోపనీయ సమాచారాన్ని చూడండి",
        "action-editmyprivateinfo": "మీ గోపనీయ సమాచారాన్ని సరిదిద్దండి",
        "action-editcontentmodel": "పేజీ యొక్క కంటెంటు మోడలును సవరించు",
-       "action-managechangetags": "à°¡à±\87à°\9fాబà±\87à°¸à±\81à°²à±\8b à°\9fà±\8dయాà°\97à±\81లనà±\81 à°\9aà±\87à°°à±\8dà°\9aà±\87 à°²à±\87దా à°¤à±\8aà°²à°\97à°¿à°\82à°\9aే",
+       "action-managechangetags": "à°\9fà±\8dయాà°\97à±\81లనà±\81 à°\9aà±\87à°°à±\8dà°\9aà±\87, (à°\85)à°\9aà±\87తనà°\82 à°\9aà±\87à°¸ే",
        "action-applychangetags": "మీ మార్పులతో ట్యాగులను ఆపాదించే",
+       "action-deletechangetags": "డేటాబేసు నుండి ట్యాగులను తొలగించే",
        "nchanges": "{{PLURAL:$1|ఒక మార్పు|$1 మార్పులు}}",
        "enhancedrc-since-last-visit": "{{PLURAL:$1|చివరి సందర్శన తరువాత}}, $1",
        "enhancedrc-history": "చరితం",
        "recentchanges-legend-heading": "<strong>సూచిక :</strong>",
        "recentchanges-legend-newpage": "{{int:recentchanges-label-newpage}} ([[Special:NewPages|కొత్త పేజీల జాబితా]]ను కూడా చూడండి)",
        "recentchanges-submit": "చూపించు",
-       "rcnotefrom": "<strong>$2</strong> నుండి జరిగిన మార్పులు (<strong>$1</strong> వరకు) కింద చూపబడ్డాయి.",
+       "rcnotefrom": "<strong>$3, $4</strong> తరువాత జరిగిన {{PLURAL:$5|మార్పు|మార్పులు}} కింద ఇచ్చాం (<strong>$1</strong> దాకా చూపించాం).",
        "rclistfrom": "$3, $2 కు ముందు  జరిగిన మార్పులను చూపించు",
        "rcshowhideminor": "చిన్న మార్పులను $1",
        "rcshowhideminor-show": "చూపించు",
        "newpageletter": "కొ",
        "boteditletter": "బా",
        "number_of_watching_users_pageview": "[వీక్షిస్తున్న సభ్యులు: {{PLURAL:$1|ఒక్కరు|$1}}]",
-       "rc_categories": "ఈ వర్గాలకు పరిమితం చెయ్యి (\"|\" తో వేరు చెయ్యండి)",
-       "rc_categories_any": "ఏదయినా",
+       "rc_categories": "ఈ వర్గాలకు పరిమితం చెయ్యి (\"|\" తో వేరు చెయ్యండి):",
+       "rc_categories_any": "à°\8eà°\82à°\9aà±\81à°\95à±\81à°¨à±\8dనది à°\8fదయినా",
        "rc-change-size-new": "మార్పు తర్వాత $1 {{PLURAL:$1|బైటు|బైట్లు}}",
        "newsectionsummary": "/* $1 */ కొత్త విభాగం",
        "rc-enhanced-expand": "వివరాలను చూపించు",
        "recentchangeslinked-summary": "ఏదైనా పేజీకి లింకై ఉన్న పేజీల్లో (లేదా ఏదైనా వర్గంలోని పేజీల్లో) జరిగిన ఇటీవలి మార్పుల జాబితా ఇది.  [[Special:Watchlist|మీ వీక్షణ జాబితా]]లో ఉన్న పేజీలు <strong>బొద్దు</strong>గా ఉంటాయి.",
        "recentchangeslinked-page": "పేజీ పేరు:",
        "recentchangeslinked-to": "లేదంటే, ఇచ్చిన పేజీకి లింకయివున్న పేజీలలో జరిగిన మార్పులను చూపించు",
+       "recentchanges-page-added-to-category": "[[:$1]] ను వర్గానికి చేర్చాం",
+       "recentchanges-page-added-to-category-bundled": "[[:$1]] వర్గానికి చేర్చబడింది, [[Special:WhatLinksHere/$1|ఈ పేజీ ఇతర పేజీల్లో చేర్చబడింది]]",
+       "recentchanges-page-removed-from-category": "[[:$1]] వర్గం నుండి తీసివేయబడింది",
+       "recentchanges-page-removed-from-category-bundled": "[[:$1]] వర్గం నుండి తీసివేయబడింది, [[Special:WhatLinksHere/$1|ఈ పేజీ ఇతర పేజీల్లో చేర్చబడింది]]",
        "upload": "దస్త్రపు ఎక్కింపు",
        "uploadbtn": "దస్త్రాన్ని ఎక్కించు",
        "reuploaddesc": "మళ్ళీ అప్‌లోడు ఫారంకు వెళ్ళు.",
        "uploaderror": "ఎక్కింపు లోపం",
        "upload-recreate-warning": "<strong>హెచ్చరిక: ఆ పేరుతో ఉన్న దస్త్రాన్ని తరలించడం లేదా తొలగించడం జరిగింది.</strong>\n\nమీ సౌకర్యం కోసం ఈ పేజీ యొక్క తొలగింపు మరియు తరలింపు చిట్టాని ఇక్కడ ఇస్తున్నాం:",
        "uploadtext": "దస్త్రాలను ఎక్కించడానికి ఈ కింది ఫారాన్ని ఉపయోగించండి.\nగతంలో ఎక్కించిన దస్త్రాలను చూడడానికి లేదా వెతకడానికి [[Special:FileList|ఎక్కించిన దస్త్రాల యొక్క జాబితా]]కు వెళ్ళండి, (పునః)ఎక్కింపులు [[Special:Log/upload|ఎక్కింపుల చిట్టా]] లోనూ తొలగింపులు [[Special:Log/delete|తొలగింపుల చిట్టా]] లోనూ కూడా నమోదవుతాయి.\n\nఒక దస్త్రాన్ని ఏదైనా పుటలో చేర్చడానికి, కింద చూపిన వాటిలో ఏదేనీ విధంగా లింకుని వాడండి:\n* దస్త్రపు పూర్తి కూర్పుని వాడడానికి '''<code><nowiki>[[</nowiki>{{ns:file}}<nowiki>:File.jpg]]</nowiki></code>'''\n* ఎడమ వైపు మార్జినులో 200 పిక్సెళ్ళ వెడల్పుగల బొమ్మ  మరియు 'ప్రత్యామ్నాయ పాఠ్యం' అన్న వివరణతో గల పెట్టె కోసం  '''<code><nowiki>[[</nowiki>{{ns:file}}<nowiki>:File.png|200px|thumb|left|ప్రత్యామ్నాయ పాఠ్యం]]</nowiki></code>'''\n* దస్త్రాన్ని చూపించకుండా నేరుగా లింకు ఇవ్వడానికి '''<code><nowiki>[[</nowiki>{{ns:media}}<nowiki>:File.ogg]]</nowiki></code>'''",
-       "upload-permitted": "à°\85à°¨à±\81మతిà°\82à°\9aà±\87 à°«à±\88à°²à±\81 à°°à°\95ాలà±\81: $1.",
+       "upload-permitted": "à°\85à°¨à±\81మతిà°\82à°\9aబడిన à°«à±\88à°²à±\81 {{PLURAL:$2|à°°à°\95à°\82|à°°à°\95ాలà±\81}}: $1.",
        "upload-preferred": "అనుమతించే ఫైలు రకాలు: $1.",
-       "upload-prohibited": "నిషà±\87ధిà°\82à°\9aà°¿à°¨ à°«à±\88à°²à±\81 à°°à°\95ాలà±\81: $1.",
+       "upload-prohibited": "నిషà±\87ధిà°\82à°\9aబడిన à°«à±\88à°²à±\81 {{PLURAL:$2|à°°à°\95à°\82|à°°à°\95ాలà±\81}}: $1.",
        "uploadlogpage": "ఎక్కింపుల చిట్టా",
        "uploadlogpagetext": "ఇటీవల జరిగిన ఫైలు అప్‌లోడుల జాబితా ఇది.\nమరింత దృశ్యాత్మకంగా చూడటం కోసం [[Special:NewFiles|కొత్త ఫైళ్ళ కొలువు]]కు వెళ్ళండి.",
        "filename": "ఫైలు పేరు",
        "largefileserver": "ఈ ఫైలు సైజు సర్వరులో విధించిన పరిమితి కంటే ఎక్కువగా ఉంది.",
        "emptyfile": "మీరు అప్‌లోడు చేసిన ఫైలు ఖాళీగా ఉన్నట్లుంది. ఫైలు పేరును ఇవ్వడంలో స్పెల్లింగు తప్పు దొర్లి ఉండొచ్చు. మీరు అప్‌లోడు చెయ్యదలచింది ఇదో కాదో నిర్ధారించుకోండి.",
        "windows-nonascii-filename": "దస్త్రాల పేర్లలో ప్రత్యేక అక్షరాలకు ఈ వికీలో అనుకూలత లేదు.",
-       "fileexists": "ఈ పేరుతో ఒక ఫైలు ఇప్పటికే ఉంది. దీనిని మార్చాలో లేదో తెలియకపోతే ఫైలు <strong>[[:$1]]</strong>ను చూడండి.\n[[$1|thumb]]",
+       "fileexists": "ఈ పేరుతో ఒక ఫైలు ఇప్పటికే ఉంది. దీనిని మార్చాలో లేదో {{GENDER:|మీకు}} తెలియకపోతే ఫైలు <strong>[[:$1]]</strong>ను చూడండి.\n[[$1|thumb]]",
        "filepageexists": "ఈ ఫైలు కొరకు వివరణ పేజీని <strong>[[:$1]]</strong> వద్ద ఈసరికే సృష్టించారు, కానీ ఆ పేరుతో ప్రస్తుతం ఫైలేదీ లేదు.\nమీరు ఇస్తున్న సంగ్రహం ఆ వివరణ పేజీలో కనబడదు. \nమీ సంగ్రహం అక్కడ కనబడాలంటే, నేరుగా అక్కడే చేర్చాలి.\n[[$1|thumb]]",
-       "fileexists-extension": "à°\87à°\9fà±\81à°µà°\82à°\9fà°¿ à°ªà±\87à°°à±\81à°¤à±\8bà°\9fà±\87 à°®à°°à±\8b à°«à±\88à°²à±\81 à°\89à°\82ది: [[$2|thumb]]\n* à°\8eà°\95à±\8dà°\95à°¿à°¸à±\8dà°¤à±\81à°¨à±\8dà°¨ à°«à±\88à°²à±\81 à°ªà±\87à°°à±\81: <strong>[[:$1]]</strong>\n* à°ªà±\8dà°°à°¸à±\8dà°¤à±\81à°¤à°\82 à°\89à°¨à±\8dà°¨ à°«à±\88à°²à±\81 à°ªà±\87à°°à±\81: <strong>[[:$2]]</strong>\nమరà±\8b à°ªà±\87à°°à±\81 à°\8eà°\82à°\9aà±\81à°\95à±\8bà°\82à°¡à°¿.",
+       "fileexists-extension": "à°\87à°\9fà±\81à°µà°\82à°\9fà°¿ à°ªà±\87à°°à±\81à°¤à±\8bà°\9fà±\87 à°®à°°à±\8b à°«à±\88à°²à±\81 à°\89à°\82ది: [[$2|thumb]]\n* à°\8eà°\95à±\8dà°\95à°¿à°¸à±\8dà°¤à±\81à°¨à±\8dà°¨ à°«à±\88à°²à±\81 à°ªà±\87à°°à±\81: <strong>[[:$1]]</strong>\n* à°ªà±\8dà°°à°¸à±\8dà°¤à±\81à°¤à°\82 à°\89à°¨à±\8dà°¨ à°«à±\88à°²à±\81 à°ªà±\87à°°à±\81: <strong>[[:$2]]</strong>\nమరిà°\82à°¤ à°µà±\88విధà±\8dయమà±\88à°¨ à°ªà±\87à°°à±\81 à°\8eà°\82à°\9aà±\81à°\95à±\81à°\82à°\9fారా?",
        "fileexists-thumbnail-yes": "ఈ ఫైలు కుదించిన బొమ్మ లాగా ఉంది ''(థంబ్‌నెయిలు)''. [[$1|thumb]]\n<strong>[[:$1]]</strong> ఫైలు చూడండి.\nగుర్తు పెట్టబడిన ఫైలు అసలు సైజే అది అయితే, మరో థంబ్‌నెయిలును అప్‌లోడు చెయ్యాల్సిన అవసరం లేదు.",
        "file-thumbnail-no": "ఫైలు పేరు <strong>$1</strong> తో మొదలవుతోంది.\nఅది పరిమాణం తగ్గించిన ''(నఖచిత్రం)'' లాగా అనిపిస్తోంది.\nఈ బొమ్మ యొక్క పూర్తి స్పష్టత కూర్పు ఉంటే, దాన్ని ఎగుమతి చెయ్యండి. లేదా ఫైలు పేరును మార్చండి.",
        "fileexists-forbidden": "ఈ పేరుతో ఇప్పటికే ఒక ఫైలు ఉంది, దాన్ని తిరగరాయలేరు.\nమీరు ఇప్పటికీ ఈ ఫైలుని ఎగుమతి చేయాలనుకుంటే, వెనక్కి వెళ్ళి మరో పేరుతో ఎగుమతి చేయండి. [[File:$1|thumb|center|$1]]",
        "undeletedrevisions": "{{PLURAL:$1|ఒక సంచిక|$1 సంచికల}} పునఃస్థాపన జరిగింది",
        "undeletedrevisions-files": "{{PLURAL:$1|ఒక కూర్పు|$1 కూర్పులు}} మరియు {{PLURAL:$2|ఒక ఫైలు|$2 ఫైళ్ళ}}ను పునస్థాపించాం",
        "undeletedfiles": "{{PLURAL:$1|ఒక ఫైలును|$1 ఫైళ్లను}} పునఃస్థాపించాం",
-       "cannotundelete": "తొలగింపు రద్దు విఫలమైంది:\n$1",
+       "cannotundelete": "తొలగింపు రద్దులు పూర్తిగానో, కొన్నిగానీ విఫలమయ్యాయి:\n$1",
        "undeletedpage": "'''$1 ను పునస్థాపించాం'''\n\nఇటీవల జరిగిన తొలగింపులు, పునస్థాపనల కొరకు [[Special:Log/delete|తొలగింపు చిట్టా]]ని చూడండి.",
        "undelete-header": "ఇటీవల తొలగించిన పేజీల కొరకు [[Special:Log/delete|తొలగింపు చిట్టా]]ని చూడండి.",
        "undelete-search-title": "తొలగించిన పేజీల అన్వేషణ",
        "blanknamespace": "(మొదటి)",
        "contributions": "{{GENDER:$1|వాడుకరి}} రచనలు",
        "contributions-title": "$1 యొక్క మార్పులు-చేర్పులు",
-       "mycontris": "మార్పుచేర్పులు",
+       "mycontris": "నా మార్పులు",
+       "anoncontribs": "యోగదానములు",
        "contribsub2": "{{GENDER:$3|$1}} ($2) కొరకు",
        "contributions-userdoesnotexist": "వాడుకరి ఖాతా \"$1\" నమోదుకాలేదు.",
        "nocontribs": "ఈ విధమైన మార్పులేమీ దొరకలేదు.",
        "sp-contributions-newbies-sub": "కొత్తవారి కోసం",
        "sp-contributions-newbies-title": "కొత్త ఖాతాల వాడుకరుల మార్పుచేర్పులు",
        "sp-contributions-blocklog": "నిరోధాల చిట్టా",
-       "sp-contributions-suppresslog": "అణచిపెట్టబడిన వాడుకరి రచనలు",
-       "sp-contributions-deleted": "తొలగించబడిన వాడుకరి రచనలు",
+       "sp-contributions-suppresslog": "అణచిపెట్టబడిన {{GENDER:$1|వాడుకరి}} రచనలు",
+       "sp-contributions-deleted": "తొలగించబడిన {{GENDER:$1|వాడుకరి}} రచనలు",
        "sp-contributions-uploads": "ఎక్కింపులు",
        "sp-contributions-logs": "చిట్టాలు",
        "sp-contributions-talk": "చర్చ",
        "whatlinkshere-prev": "{{PLURAL:$1|మునుపటిది|మునుపటి $1}}",
        "whatlinkshere-next": "{{PLURAL:$1|తరువాతది|తరువాతి $1}}",
        "whatlinkshere-links": "← లంకెలు",
-       "whatlinkshere-hideredirs": "దారిమార్పులను $1",
+       "whatlinkshere-hideredirs": "$1 దారిమార్పులు",
        "whatlinkshere-hidetrans": "$1 ట్రాన్స్‌క్లూజన్లు",
-       "whatlinkshere-hidelinks": "లింకులను $1",
+       "whatlinkshere-hidelinks": "$1 లింకులు",
        "whatlinkshere-hideimages": "$1 దస్త్రాల లంకెలు",
        "whatlinkshere-filters": "వడపోతలు",
        "whatlinkshere-submit": "వెళ్ళు",
        "javascripttest": "జావాస్క్రిప్ట్ పరీక్ష",
        "javascripttest-pagetext-unknownaction": "తెలియని చర్య \"$1\".",
        "javascripttest-qunit-intro": "mediawiki.org లోని [$1 పరీక్షా డాక్యుమెంటేషన్] చూడండి.",
-       "tooltip-pt-userpage": "మీ వాడుకరి పేజీ",
+       "tooltip-pt-userpage": "{{GENDER:|మీ వాడుకరి}} పేజీ",
        "tooltip-pt-anonuserpage": "మీ ఐపీ చిరునామాకి సంబంధించిన వాడుకరి పేజీ",
-       "tooltip-pt-mytalk": "మీ చర్చా పేజీ",
+       "tooltip-pt-mytalk": "{{GENDER:|మీ}} చర్చా పేజీ",
        "tooltip-pt-anontalk": "ఈ ఐపీ చిరునామా నుండి చేసిన మార్పుల గురించి చర్చ",
-       "tooltip-pt-preferences": "మీ అభిరుచులు",
+       "tooltip-pt-preferences": "{{GENDER:|మీ}} అభిరుచులు",
        "tooltip-pt-watchlist": "మీరు మార్పుల కొరకు గమనిస్తున్న పేజీల జాబితా",
-       "tooltip-pt-mycontris": "మీ మార్పుచేర్పుల జాబితా",
+       "tooltip-pt-mycontris": "{{GENDER:|మీ}} యోగదానములు",
        "tooltip-pt-login": "మిమ్మల్ని లాగినవమని ప్రోత్సహిస్తున్నాం; కానీ అది తప్పనిసరేమీ కాదు.",
        "tooltip-pt-logout": "లాగౌటవండి",
        "tooltip-pt-createaccount": "మీరొక ఖాతాని సృష్టించుకొని ప్రవేశించటాన్ని సమర్ధిస్తున్నాము; కానీ, అది అవసరం కాదు, ఐచ్ఛికం మాత్రమే.",
        "tooltip-t-recentchangeslinked": "ఈ పేజీకి లింకై ఉన్న పేజీల్లో జరిగిన ఇటీవలి మార్పులు",
        "tooltip-feed-rss": "ఈ పేజీకి RSS ఫీడు",
        "tooltip-feed-atom": "ఈ పేజీకి Atom ఫీడు",
-       "tooltip-t-contributions": "à°\88 à°µà°¾à°¡à±\81à°\95à°°à°¿ à°¯à±\8aà°\95à±\8dà°\95 à°°à°\9aనల à°\9cాబితా à°\9aà±\82à°¡à°\82à°¡à°¿",
+       "tooltip-t-contributions": "à°¯à±\8bà°\97దానమà±\81à°²à±\81 à°\9cాబితాâ\80\8c {{GENDER:$1|à°\88 à°µà°¾à°¡à±\81à°\95à°°à°¿}}",
        "tooltip-t-emailuser": "ఈ వాడుకరికి ఓ ఈమెయిలు పంపండి",
        "tooltip-t-info": "ఈ పేజీ గురించి మరింత సమాచారం",
        "tooltip-t-upload": "దస్త్రాలను ఎక్కించండి",
index 23c10a3..464655a 100644 (file)
@@ -24,7 +24,8 @@
                        "Pphongpan355",
                        "Macofe",
                        "Pilarbini",
-                       "Matma Rex"
+                       "Matma Rex",
+                       "B20180"
                ]
        },
        "tog-underline": "การขีดเส้นใต้ลิงก์:",
        "laggedslavemode": "<strong>คำเตือน:</strong> หน้านี้อาจไม่มีการปรับล่าสุด",
        "readonly": "ฐานข้อมูลถูกล็อก",
        "enterlockreason": "ใส่เหตุแห่งการล็อก ทั้งเวลาที่คาดว่าจะปลดล็อก",
-       "readonlytext": "à¸\82à¸\93ะà¸\99ีà¹\89à¸\90าà¸\99à¸\82à¹\89อมูลà¸\96ูà¸\81ลà¹\87อà¸\81มิà¹\83หà¹\89รัà¸\9aà¸\82à¹\89อมูลใหม่และการแก้ไขเพิ่มเติมอื่น อาจเป็นเพราะการบำรุงรักษาฐานข้อมูลรูทีน หลังแล้วเสร็จจะกลับมาใช้งานได้ตามปกติ\n\nผู้ดูแลระบบที่ล็อกได้ให้คำอธิบายดังนี้: $1",
+       "readonlytext": "à¸\82à¸\93ะà¸\99ีà¹\89à¸\90าà¸\99à¸\82à¹\89อมูลà¸\96ูà¸\81ลà¹\87อà¸\81รายà¸\81ารใหม่และการแก้ไขเพิ่มเติมอื่น อาจเป็นเพราะการบำรุงรักษาฐานข้อมูลรูทีน หลังแล้วเสร็จจะกลับมาใช้งานได้ตามปกติ\n\nผู้ดูแลระบบที่ล็อกได้ให้คำอธิบายดังนี้: $1",
        "missing-article": "ฐานข้อมูลไม่พบข้อความของหน้าที่ควรมี ชื่อ \"$1\" $2\n\nสาเหตุมักเกิดจากผลต่างที่ล้าสมัย หรือการเชื่อมโยงประวัติไปยังหน้านั้นถูกลบแล้ว\n\nหากไม่ใช่กรณีดังกล่าว คุณอาจพบจุดบกพร่องในซอฟต์แวร์ กรุณารายงานต่อ[[Special:ListUsers/sysop|ผู้ดูแลระบบ]] พร้อมระบุยูอาร์แอล",
        "missingarticle-rev": "(รุ่นปรับปรุง#: $1)",
        "missingarticle-diff": "(ต่าง: $1, $2)",
        "protectedinterface": "หน้านี้เป็นข้อความส่วนต่อประสานสำหรับซอฟต์แวร์บนวิกินี้ และถูกล็อกเพื่อป้องกันการกระทำผิด\nในการเพิ่มหรือเปลี่ยนแปลงการแปลสำหรับทุกวิกิ โปรดใช้ [https://translatewiki.net/ translatewiki.net] โครงการแปลมีเดียวิกิเป็นภาษาถิ่น",
        "editinginterface": "<strong>คำเตือน:</strong> คุณกำลังแก้ไขหน้าที่ใช้จัดหาข้อความอินเตอร์เฟซให้ซอฟต์แวร์\nการเปลี่ยนแปลงหน้านี้จะมีผลต่อสภาพปรากฏของส่วนต่อประสานผู้ใช้แก่ผู้ใช้อื่นบนวิกินี้",
        "translateinterface": "ในการเพิ่มหรือเปลี่ยนแปลงคำแปลสำหรับทุกวิกิ โปรดใช้ [https://translatewiki.net/ translatewiki.net] โครงการแปลเป็นภาษาถิ่นของมีเดียวิกิ",
-       "cascadeprotected": "หน้านี้ถูกป้องกันมิให้แก้ไข เพราะถูกรวมอยู่ในหน้าต่อไปนี้ซึ่งถูกล็อกโดยเปิดตัวเลือก \"ต่อเรียง\":\n$2",
+       "cascadeprotected": "หน้านี้ถูกป้องกันมิให้แก้ไข เพราะถูกรวมอยู่ใน{{PLURAL:$1|page, which is|หน้าต่อไปนี้}} ซึ่งถูกล็อกโดยเปิดตัวเลือก \"ต่อเรียง\":\n$2",
        "namespaceprotected": "คุณไม่มีสิทธิแก้ไขหน้าในเนมสเปซ <strong>$1</strong>",
        "customcssprotected": "คุณไม่มีสิทธิแก้ไขหน้า CSS นี้ เพราะมีการตั้งค่าส่วนบุคคลของผู้ใช้อื่น",
        "customjsprotected": "คุณไม่มีสิทธิแก้ไขหน้าจาวาสคริปต์นี้ เพราะหน้านี้มีการตั้งค่าส่วนบุคคลของผู้ใช้อื่น",
        "passwordreset-emailelement": "ชื่อผู้ใช้: \n$1\n\nรหัสผ่านชั่วคราว: \n$2",
        "passwordreset-emailsentemail": "หากที่อยู่อีเมลนี้สัมพันธ์กับบัญชีของคุณ เช่นนั้นจะส่งอีเมลตั้งรหัสผ่านใหม่",
        "passwordreset-emailsentusername": "หากมีที่อยู่อีเมลที่ลงทะเบียนไว้ด้วยกับชื่อผู้ใช้นี้ เช่นนั้นจะส่งอีเมลตั้งรหัสผ่านใหม่",
-       "passwordreset-emailsent-capture": "อีเมลตั้งรหัสผ่านใหม่ถูกส่งไปแล้ว ซึ่งแสดงด้านล่าง",
-       "passwordreset-emailerror-capture": "อีเมลตั้งรหัสผ่านใหม่ถูกสร้างขึ้นแล้ว ซึ่งแสดงด้านล่าง แต่ไม่สามารถส่งไปยัง{{GENDER:$2|ผู้ใช้}}: $1",
        "changeemail": "เปลี่ยนหรือลบที่อยู่อีเมล",
        "changeemail-header": "กรอกแบบนี้เพื่อเปลี่ยนที่อยู่อีเมลของคุณ หากคุณต้องการลบการเชื่อมโยงของที่อยู่อีเมลใด ๆ จากบัญชีของคุณ ให้เว้นที่อยู่อีเมลใหม่ว่างเมื่อส่งแบบ",
-       "changeemail-passwordrequired": "คุณจะต้องกรอกรหัสผ่านใหม่เพื่อยืนยันการเปลี่ยนแปลงนี้",
        "changeemail-no-info": "คุณจำต้องล็อกอินเพื่อเข้าถึงหน้านี้โดยตรง",
        "changeemail-oldemail": "ที่อยู่อีเมลปัจจุบัน:",
        "changeemail-newemail": "ที่อยู่อีเมลใหม่:",
        "undo-nochange": "ดูเหมือนว่าการแก้ไขดังกล่าวถูกย้อนกลับแล้ว",
        "undo-summary": "ทำกลับรุ่นแก้ไข $1 โดย [[Special:Contributions/$2|$2]] ([[User talk:$2|พูดคุย]])",
        "undo-summary-username-hidden": "ทำกลับรุ่นแก้ไข $1 โดยผู้ใช้ไม่ระบุชื่อ",
-       "cantcreateaccounttitle": "ไม่สามารถสร้างบัญชีได้",
        "cantcreateaccount-text": "การสร้างบัญชีใหม่จากที่อยู่ไอพีนี้ ('''$1''') ถูกระงับโดย [[User:$3|$3]]\n\nเหตุผลที่ $3 ให้ไว้ คือ ''$2''",
        "cantcreateaccount-range-text": "การสร้างบัญชีจากเลขที่อยู่ไอพีในช่วง <strong>$1</strong> ซึ่งรวมเลขที่อยู่ไอพีของคุณ (<strong>$4</strong>) ถูกบล็อกโดย [[User:$3|$3]] \n\nเหตุผลที่ $3 ชี้แจง คือ <em>$2</em>",
        "viewpagelogs": "ดูปูมของหน้านี้",
        "special-characters-group-bangla": "บังคลา",
        "special-characters-group-telugu": "เตลูกู",
        "special-characters-group-sinhala": "สิงหล",
-       "special-characters-group-gujarati": "คุชราต",
-       "api-error-blacklisted": "โปรดใช้ชื่ออื่นที่สื่อความหมาย"
+       "special-characters-group-gujarati": "คุชราต"
 }
index 8c0ed14..20aea78 100644 (file)
        "print": "Yazdır",
        "view": "Görüntüle",
        "view-foreign": "$1 üzerinde gör",
-       "edit": "Değiştir",
+       "edit": "Düzenle",
        "edit-local": "Yerel açıklamayı düzenle",
        "create": "Oluştur",
        "create-local": "Yerel açıklama ekle",
        "passwordreset-emailelement": "Kullanıcı adı: \n$1\n\nGeçici şifre: \n$2",
        "passwordreset-emailsentemail": "Eğer bu e-posta adresi hesabınızın bağlı olduğu adres ise, bir parola sıfırlama e-postası gönderilecektir.",
        "passwordreset-emailsentusername": "Eğer bu e-posta adresi hesabınızın bağlı olduğu adres ise, bir parola sıfırlama e-postası gönderilecektir.",
-       "passwordreset-emailsent-capture": "Aşağıda gözüktüğü gibi bir parola sıfırlama e-postası gönderildi.",
-       "passwordreset-emailerror-capture": "Aşağıda gözüktüğü gibi bir parola sıfırlama e-postası oluşturuldu ancak {{GENDER:$2|kullanıcıya}} gönderme işlemi başarısız oldu: $1",
        "passwordreset-invalideamil": "Geçersiz e-posta adresi",
        "passwordreset-nodata": "Ne bir kullanıcı adı ne de bir e-posta adresi verildi.",
        "changeemail": "E-posta adresini değiştir veya çıkar",
        "changeemail-header": "E-posta adresinizi değiştirmek için bu formu doldurun. Eğer e-posta adresini hesabınızdan kaldırmak istiyorsanız formu gönderirken e-posta adresi bölümünü boş bırakın.",
-       "changeemail-passwordrequired": "Bu değişikliği onaylamak için şifrenizi girmeniz gerekir.",
        "changeemail-no-info": "Bu sayfaya doğrudan erişmek için oturum açmanız gereklidir.",
        "changeemail-oldemail": "Mevcut E-posta adresi:",
        "changeemail-newemail": "Yeni E-posta adresi:",
        "undo-nochange": "Düzeltme zaten geri alınmış.",
        "undo-summary": "$1 değişikliği [[Special:Contributions/$2|$2]] ([[User talk:$2|mesaj]]) tarafından geri alındı.",
        "undo-summary-username-hidden": "Gizli bir kullanıcı tarafından $1 sürümü geri alınıyor",
-       "cantcreateaccounttitle": "Hesap açılamıyor",
        "cantcreateaccount-text": "Bu IP adresinden ('''$1''') kullanıcı hesabı oluşturulması [[User:$3|$3]] tarafından engellenmiştir.\n\n$3 tarafından verilen sebep ''$2''",
        "cantcreateaccount-range-text": "<strong>$1</strong> aralığındaki IP'ler için hesap oluşturma [[User:$3|$3]] tarafından engellendi, bu sizin IP adresinizi de (<strong>$4</strong>) içeriyor.\n\n$3 tarafından verilen gerekçe <em>$2</em>",
        "viewpagelogs": "Bu sayfa ile ilgili kayıtları göster",
index 128db0e..0af6224 100644 (file)
        "passwordreset-emailtext-user": "{{SITENAME}} проектыннан $1 кулланучысы {{SITENAME}} ($4) проектында сезнең серсүзне искә төшерүне сорады.\n{{PLURAL:$3|1=Түбәндәге хисап язмасы|Түбәндәге хисап язмалары}} бу электрон әрҗә адресы белән бәйле:\n\n$2\n\n{{PLURAL:$3|1=Бу вакытлы серсүз|Бу вакытлы серсүзләр}} {{PLURAL:$5|$5 көн}} дәвамында эшлиячәкләр.\nСез системага керергә һәм яңа серсүз сайларга тиешсез.\nӘгәр сез серсүз сорамаган булсагыз яки элеккеге серсүзегезне искә төшерсәгез \nһәм аны үзгәртергә теләмәсәгез, бу хатка җавап бирмәгез\nһәм элеккеге серсүзегезне кулланыгыз.",
        "passwordreset-emailelement": "Кулланучы исеме: \n$1\n\nВакытлыча серсүз: \n$2",
        "passwordreset-emailsentemail": "Әгәрдә бу электрон әрҗәгез сезнең хисап язмагыз белән бәйләнгән булса,сезгә серсүзне яңарту өчен хат җибәреләчәк.",
-       "passwordreset-emailsent-capture": "Серсүзне яңарту турындагы мәгълүмәт электрон хат белән сезгә җибәрелде, аның текстын түбәндә карарга мөмкин.",
-       "passwordreset-emailerror-capture": "Серсүзне яңарту турында хәбәр итече хат ясалды, ләкин аны  {{GENDER:$2|кулланучыга}} түбәндәге сәбәп аркасында җибәре булмады: $1",
        "changeemail": "Электрон әрҗә адресын үзгәртү яисә бетерү",
        "changeemail-header": "Электрон әрҗә адресын үзгәртү өчен әлеге форманы тутырыгыз. Әгәрдә сез электрон әрҗәгезне хисап язмагыздан өзәсегез килмәсә, форманы тутырганда яңа адрес урынын буш калдырыгыз.",
-       "changeemail-passwordrequired": "Әлеге үзгәрешләрне раслау өчен, Сезгә кулланылучы серсүзне язарга кирәк.",
        "changeemail-no-info": "Бу сәхифәгә турыдан-туры мөрәҗәгать итәр өчен, сез системага керергә тиешсез",
        "changeemail-oldemail": "Хәзерге электрон әрҗә адресы:",
        "changeemail-newemail": "Яңа электрон почта адресы:",
        "undo-failure": "Аралыктагы үзгәртүләр туры килмәү сәбәпле, үзгәртүдән баш тартып булмый.",
        "undo-norev": "Үзгәртү юк яисә ул бетерелгән, шуңа аннан баш тартып булмый.",
        "undo-summary": "[[Special:Contributions/$2|$2]] кулланучысының ([[User talk:$2|бәхәс]]) $1 үзгәртүеннән баш тарту",
-       "cantcreateaccounttitle": "Хисап язмасын төзеп булмый",
        "cantcreateaccount-text": "Бу IP адресыннан (<b>$1</b>) хисап язмалары төзү тыела. Тыючы: [[User:$3|$3]].\n\n$3 күрсәткән сәбәп: ''$2''",
        "viewpagelogs": "Бу битнең көндәлекләрен карау",
        "nohistory": "Бу битнең үзгәртүләр тарихы юк.",
index 45a58d2..c601325 100644 (file)
        "passwordreset-emailelement": "Ім'я користувача: \n$1\n\nТимчасовий пароль: \n$2",
        "passwordreset-emailsentemail": "Якщо ця електронна адреса асоційована з вашим обліковим записом, то лист для відновлення пароля буде відправлено на неї.",
        "passwordreset-emailsentusername": "Якщо існує електронна адреса, яка асоційована з цим обліковим записом, на неї буде надіслано лист для відновлення пароля.",
-       "passwordreset-emailsent-capture": "Електронний лист скидання пароля було надіслано, як показано нижче.",
-       "passwordreset-emailerror-capture": "Електронний лист для відновлення пароля мав бути надісланий, як показано нижче, але його надсилання {{GENDER:$2|користувачеві|користувачці}} $1 не вдалося.",
        "passwordreset-emailsent-capture2": "{{PLURAL:$1|Електронний лист|Електронні листи}} скидання паролю було надіслано. {{PLURAL:$1|Ім'я користувача і пароль|Список імен користувачів і паролів}} показано нижче.",
        "passwordreset-emailerror-capture2": "Не вдалося надіслати листа {{GENDER:$2|користувачу|користувачці}}: $1 {{PLURAL:$3|Ім'я користувача і пароль|список імен користувачів і паролів}} показано нижче.",
        "passwordreset-nocaller": "Має бути надане джерело виклику",
        "passwordreset-nodata": "Не надано ні імені користувача, ні електронної адреси",
        "changeemail": "Змінити або вилучити адресу електронної пошти",
        "changeemail-header": "Заповніть цю форму, щоб змінити адресу електронної пошти. Якщо Ви хочете взагалі прибрати зв'язок свого облікового запису з адресою електронної пошти, при надсиланні форми залиште поле нової електронної адреси порожнім.",
-       "changeemail-passwordrequired": "Вам потрібно буде ввести пароль, щоб підтвердити цю зміну.",
        "changeemail-no-info": "Ви повинні увійти в систему, щоб отримати безпосередній доступ до цієї сторінки.",
        "changeemail-oldemail": "Поточна адреса електронної пошти:",
        "changeemail-newemail": "Нова адреса електронної пошти:",
        "undo-nochange": "Схоже, редагування вже було скасовано.",
        "undo-summary": "Скасування редагування № $1 користувача [[Special:Contribs/$2|$2]] ([[User talk:$2|обговорення]])",
        "undo-summary-username-hidden": "Скасувати версію $1, виконану прихованим користувачем",
-       "cantcreateaccounttitle": "Неможливо створити обліковий запис",
        "cantcreateaccount-text": "Створення облікових записів із цієї IP-адреси ('''$1''') було заблоковане [[User:$3|користувачем $3]].\n\n$3 зазначив таку причину: ''$2''",
        "cantcreateaccount-range-text": "Створення облікового запису із IP-адрес у діапазоні  <strong>$1</strong>, який включає вашу IP-адресу (<strong>$4</strong>), було заблоковано користувачем [[User:$3|$3]].\n\nКористувач $3 вказав як причину <em>$2</em>",
        "viewpagelogs": "Показати журнали для цієї сторінки",
        "uploadstash-errclear": "Очищення файлів зазнало невдачі.",
        "uploadstash-refresh": "Оновити список файлів",
        "uploadstash-thumbnail": "перегляд мініатюри",
+       "uploadstash-exception": "Не вдалося зберегти завантаження у сховку ($1): «$2».",
        "invalid-chunk-offset": "Неприпустимий зсув фрагмента",
        "img-auth-accessdenied": "Відмовлено в доступі",
        "img-auth-nopathinfo": "Відсутній PATH_INFO.\nВаш сервер не налаштовано для передачі цих даних.\nМожливо, він працює на основі CGI та не підтримує img_auth.\nПерегляньте [https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization Відкриття доступу до зображень]",
        "listgrants-summary": "Нижче наведено список дозволів, з їхнім пов'язаним доступом до прав користувача. Користувачі можуть дозволити програмам використовувати свій обліковий запис, але з обмеженими правами на основі грантів користувача наданих до заяви. Програма діє від імені користувача, однак насправді не може використовувати права, які користувач не має.\nМоже бути [[{{MediaWiki:Listgrouprights-helppage}}|додаткова інформація]] про індивідуальні права.",
        "listgrants-grant": "Грант",
        "listgrants-rights": "Права",
-       "trackingcategories": "Ð\92Ñ\96дÑ\81Ñ\82ежÑ\83ванÑ\96 ÐºÐ°Ñ\82егоÑ\80Ñ\96Ñ\97",
+       "trackingcategories": "Ð\9aаÑ\82егоÑ\80Ñ\96Ñ\97 Ñ\81поÑ\81Ñ\82еÑ\80еженнÑ\8f",
        "trackingcategories-summary": "На цій сторінці перераховані відстежують категорії, які заповнюються автоматично програмним забезпеченням MediaWiki. Їх можна перейменувати, змінивши відповідні системні повідомлення в просторі назв {{ns:8}}.",
        "trackingcategories-msg": "Відстежувана категорія",
        "trackingcategories-name": "Ім'я повідомлення",
        "undeletehistorynoadmin": "Стаття вилучена. Причина вилучення та список користувачів, що редагували статтю до вилучення, вказані нижче. Текст вилученої статті можуть переглянути лише адміністратори.",
        "undelete-revision": "Вилучена версія $1 (від $4 $5) користувача $3:",
        "undeleterevision-missing": "Невірна версія. Помилкове посилання, або вказану версію сторінки вилучено з архіву.",
+       "undeleterevision-duplicate-revid": "{{PLURAL:$1|Одну версію|$1 версії|$1 версій}} не вдалося відновити, оскільки {{PLURAL:$1|її|їхній}} <code>rev_id</code> вже використовується.",
        "undelete-nodiff": "Не знайдена попередня версія.",
        "undeletebtn": "Відновити",
        "undeletelink": "переглянути/відновити",
        "undeletedrevisions": "$1 {{PLURAL:$1|редагування|редагування|редагувань}} відновлено",
        "undeletedrevisions-files": "$1 {{PLURAL:$1|версія|версії|версій}} та $2 {{PLURAL:$2|файл|файли|файлів}} відновлено",
        "undeletedfiles": "$1 {{PLURAL:$1|файл|файли|файлів}} відновлено",
-       "cannotundelete": "Ð\9fомилка Ð²Ñ\96дновленнÑ\8f:\n$1",
+       "cannotundelete": "ЧаÑ\81Ñ\82ина Ð°Ð±Ð¾ Ð²Ñ\81Ñ\8f Ð¿Ñ\80оÑ\86едÑ\83Ñ\80а Ð²Ñ\96дновленнÑ\8f Ð·Ð°Ð·Ð½Ð°Ð»Ð° Ð½ÐµÐ²Ð´Ð°Ñ\87Ñ\96:\n$1",
        "undeletedpage": "'''Сторінка «$1» відновлена'''\n\nДив. [[Special:Log/delete|список вилучень]], щоб дізнатися про останні вилучення та відновлення.",
        "undelete-header": "Список нещодавно вилучених сторінок можна переглянути в [[Special:Log/delete|журналі вилучень]].",
        "undelete-search-title": "Пошук видалених сторінок",
        "sp-contributions-newbies-sub": "Внесок новачків",
        "sp-contributions-newbies-title": "Внесок з нових облікових записів",
        "sp-contributions-blocklog": "журнал блокувань",
-       "sp-contributions-suppresslog": "вилÑ\83Ñ\87ений Ð²Ð½ÐµÑ\81ок ÐºÐ¾Ñ\80иÑ\81Ñ\82Ñ\83ваÑ\87а",
-       "sp-contributions-deleted": "вилучені редагування користувача",
+       "sp-contributions-suppresslog": "пÑ\80иÑ\85ований Ð²Ð½ÐµÑ\81ок {{GENDER:$1|коÑ\80иÑ\81Ñ\82Ñ\83ваÑ\87а|коÑ\80иÑ\81Ñ\82Ñ\83ваÑ\87ки}}",
+       "sp-contributions-deleted": "вилучені редагування {{GENDER:$1|користувача|користувачки}}",
        "sp-contributions-uploads": "завантаження",
        "sp-contributions-logs": "журнали",
        "sp-contributions-talk": "обговорення",
index 882ea01..42c3a28 100644 (file)
        "passwordreset-emailtext-user": "El utente $1 da {{SITENAME}} (probabilmente ti steso) ga richiesto l'invio de na password nova par {{SITENAME}} ($4). {{PLURAL:$3|El profiło utente asocià|I profiłi utenti asociadi}} a sto indiriso de posta ełetronega łi xe:\n\n$2\n\n{{PLURAL:$3|Sta password tenporanea ła scadarà|Ste password tenporanee łe scadarà}} dopo {{PLURAL:$5|un dì|$5 dì}}.\n\nSarìa mejo acedare e deçidare na nova password sùito. Se no te si stà ti a fare ła richiesta, o se te te ghe ricordà ła password originałe e no te vołi pi canbiarla, te połi ignorare sto mesajo e continuar doparare ła to password vecia.",
        "passwordreset-emailelement": "Nome utente: \n$1\n\nPassword tenporanea: \n$2",
        "passwordreset-emailsentemail": "Xe stà invià na mail de reset password.",
-       "passwordreset-emailsent-capture": "Xe stà invià na mail de reset password: el contegù xe riportà cuà de seguito.",
-       "passwordreset-emailerror-capture": "Xe stà generà na mail de reset password, riportà cuà de seguito. L'invio a {{GENDER:$2|l'utente}} no xe riusido: $1",
        "changeemail": "Canbia indiriso de posta ełetronega",
        "changeemail-header": "Canbia el indiriso de posta ełetronega del account",
        "changeemail-no-info": "Te ghe da aver efetuà l'aceso par acedare a sta pajina diretamente.",
        "minoredit": "Segna come canbiamento picenin",
        "watchthis": "Tien d'ocio sta pagina",
        "savearticle": "Salva sta pagina",
+       "publishpage": "Pùblica la pàjina",
+       "publishchanges": "Pùblica i to canbiamenti",
        "preview": "Anteprima",
        "showpreview": "Varda anteprima",
        "showdiff": "Mostra canbiamenti",
        "undo-failure": "No se pol mìa anular la modifica, par via de un conflito con modifiche intermedie.",
        "undo-norev": "La modifica no la pode vegner anulà parché no la esiste o la xe stà scancelà.",
        "undo-summary": "Anulà la modifica $1 de [[Special:Contributions/$2|$2]] ([[User talk:$2|Discussion]] | [[Special:Contributions/$2|{{MediaWiki:Contribslink}}]])",
-       "cantcreateaccounttitle": "Inpossibile registrar l'utente",
        "cantcreateaccount-text": "La creazion de account novi a partir da sto indirizo IP ('''$1''') la xe stà blocà da [[User:$3|$3]].\n\nLa motivazion del bloco fornìa da $3 la xe sta qua: ''$2''",
        "viewpagelogs": "Varda i registri de sta pagina",
        "nohistory": "La cronołogia de łe version de sta pàxena no la xè reperibiłe.",
        "mw-widgets-dateinput-placeholder-day": "AAAA-MM-GG",
        "mw-widgets-dateinput-placeholder-month": "AAAA-MM",
        "mw-widgets-titleinput-description-redirect": "rimando a $1",
-       "api-error-blacklisted": "Par piaser siełi un titoło difarente e descritivo.",
        "randomrootpage": "Pagina raìsa caxuale"
 }
index 7551378..14059a5 100644 (file)
        "passwordreset-emailelement": "Tên người dùng: \n$1\n\nMật khẩu tạm: \n$2",
        "passwordreset-emailsentemail": "Nếu đây là đúng địa chỉ thư điện tử của tài khoản của bạn, một thư điện tử dùng để tái tạo mật khẩu sẽ được gửi cho bạn.",
        "passwordreset-emailsentusername": "Nếu một địa chỉ thư điện tử đã gắn với tên người dùng này thì một thư điện tử để đặt lại mật khẩu sẽ được gửi đến.",
-       "passwordreset-emailsent-capture": "Thư điện tử để tái tạo mật khẩu đã được gửi, nội dung như sau.",
-       "passwordreset-emailerror-capture": "Chúng tôi đã tạo thư tái tạo mật khẩu dưới đây, nhưng không thể gửi đến {{GENDER:$2}}người dùng: $1",
        "passwordreset-emailsent-capture2": "Đã gửi {{PLURAL:$1|thư điện tử|các thư điện tử}} để đặt lại mật khẩu. {{PLURAL:$1|Tên người dùng và mật khẩu|Các tên người dùng và mật khẩu}} được liệt kê dưới đây.",
        "passwordreset-emailerror-capture2": "Không gửi được thư điện tử đến {{GENDER:$2}}người dùng: $1 {{PLURAL:$3|Tên người dùng và mật khẩu|Các tên người dùng và mật khẩu}} được liệt kê dưới đây.",
        "passwordreset-nocaller": "Yêu cầu hàm gọi",
        "passwordreset-nodata": "Cả tên người dùng và địa chỉ thư điện tử bị thiếu",
        "changeemail": "Đổi hoặc gỡ địa chỉ thư điện tử",
        "changeemail-header": "Điền biểu mẫu này để đổi địa chỉ thư điện tử của bạn. Nếu bạn muốn gỡ địa chỉ thư điện tử nào khỏi tài khoản của bạn, để trống hộp địa chỉ thư điện tử mới và lưu biểu mẫu.",
-       "changeemail-passwordrequired": "Bạn sẽ cần phải nhập mật khẩu của bạn để xác nhận thay đổi này.",
        "changeemail-no-info": "Bạn phải đăng nhập mới có thể truy cập trực tiếp trang này.",
        "changeemail-oldemail": "Địa chỉ thư điện tử hiện tại:",
        "changeemail-newemail": "Địa chỉ thư điện tử mới:",
        "undo-nochange": "Hình như sửa đổi này đã được lùi lại rồi.",
        "undo-summary": "Đã lùi lại sửa đổi $1 của [[Special:Contributions/$2|$2]] ([[User talk:$2|thảo luận]])",
        "undo-summary-username-hidden": "Đã lùi lại sửa đổi $1 của một người dùng ẩn",
-       "cantcreateaccounttitle": "Không thể mở tài khoản",
        "cantcreateaccount-text": "Chức năng tài tạo khoản từ địa chỉ IP này ('''$1''') đã bị [[User:$3|$3]] cấm.\n\nLý do được $3 đưa ra là ''$2''",
        "cantcreateaccount-range-text": "[[User:$3|$3]] đã cấm các địa chỉ IP trong dãy <strong>$1</strong>, bao gồm địa chỉ IP của bạn (<strong>$4</strong>), không được mở tài khoản.\n\nLý do được đưa ra bởi $3 là <em>$2</em>",
        "viewpagelogs": "Xem nhật trình của trang này",
index 4edc5d8..e9877a5 100644 (file)
        "createacct-emailoptional": "电子信地址(填弗填由你)",
        "createacct-email-ph": "畀你侬个电子信地址打进去",
        "createacct-another-email-ph": "电子信地址打进去",
-       "createaccountmail": "用临时随便密码发到指定个电子信地址",
+       "createaccountmail": "拿临时随机密码发到指定个电邮地址",
        "createacct-realname": "真名字(随意)",
        "createaccountreason": "理由:",
        "createacct-reason": "理由:",
        "passwordreset-emailtitle": "{{SITENAME}}上个账号详细信息",
        "passwordreset-emailelement": "用户名:\n$1\n\n临时密码:\n$2",
        "changeemail": "更改或删脱电子邮箱地址",
-       "changeemail-passwordrequired": "侬需要输入密码来确认本次更改。",
        "changeemail-no-info": "侬必须登录著才好直接进入箇只页面。",
        "changeemail-oldemail": "当前电子邮件地址:",
        "changeemail-newemail": "新个电子邮件地址:",
        "session_fail_preview": "弗好意思!由于会话数据落失,我伲弗好处理侬个编辑。\n\n侬作兴已经登出哉。<strong>请核实侬啊曾登录勒上,再试一遍</strong>。如果仍旧弗来事,请[[Special:UserLogout|登出]]著再重新登录,并确保侬个浏览器允许本站个cookie。",
        "session_fail_preview_html": "弗好意思!因为会话数据落失,我伲弗好处理侬个编辑。\n\n<em>由于{{SITENAME}}允许使用原始个HTML,为著防范JavaScript攻击,预览已经囥脱。</em>\n\n<strong>如果箇是一趟合法个编辑,请再试一遍。</strong>如果仍旧弗来事,请[[Special:UserLogout|登出]]著再重新登录,并确保侬个浏览器允许本站个cookie。",
        "token_suffix_mismatch": "<strong>由于侬用户端里向个编辑令牌毁损仔一些标点符号字元,为防止编辑个文字损坏,侬个编辑已经畀回头。</strong>箇种情况通常出现垃拉使用含有交关bug、以网络为主个匿名代理服务个辰光。",
-       "editing": "来里编写$1",
+       "editing": "来里编写“$1”",
        "creating": "创建“$1”",
-       "editingsection": "来里编辑$1(段落)",
+       "editingsection": "来里编写“$1”(段落)",
        "editingcomment": "垃许编辑 $1 (新段落)",
        "editconflict": "编辑冲突: $1",
        "explainconflict": "有人垃拉侬开始编辑之后更改仔页面。上头个文字框内显示个是箇歇本页个内容。侬个修改显示垃拉下底只文字框里向。侬应当拿侬个修改合并到现有个文本里向。<strong>只有</strong>上头文字框里向个内容会得垃侬点击“{{int:savearticle}}”之后畀保存。",
        "node-count-exceeded-category": "页面个节点数超出限制",
        "parser-unstrip-recursion-limit": "递归超过限制 ($1)",
        "converter-manual-rule-error": "来手动语言转换规则当中查着错误",
-       "undo-success": "箇只编辑可以撤销。\n请检查下头个比较,确定侬确实想撤销,然后保存下底个更改完成撤销编辑。",
+       "undo-success": "箇只编辑可以撤销。请检查下头个比较,确定侬确实想撤销,再保存下底个更改完成撤销编辑。",
        "undo-failure": "由于相互冲突个中途编辑,箇只编辑弗好撤销。",
        "undo-norev": "由于其版本弗存在或已删除,此编辑弗好撤销。",
        "undo-nochange": "箇届编辑看出来已经畀撤销。",
        "undo-summary": "撤销由[[Special:Contributions/$2|$2]]([[User talk:$2|讨论]])作出个版本$1",
-       "cantcreateaccounttitle": "弗好开户",
        "cantcreateaccount-text": "从箇只IP地址 (<b>$1</b>) 创建账户已经畀[[User:$3|$3]]禁止。\n\n$3封禁个原因是''$2''",
        "viewpagelogs": "望箇页日志",
        "nohistory": "该只页面呒不编辑历史。",
        "rc-enhanced-hide": "拿细节囥脱",
        "recentchangeslinked": "搭界个改动",
        "recentchangeslinked-feed": "搭界个改动",
-       "recentchangeslinked-toolbox": "相关变化",
+       "recentchangeslinked-toolbox": "搭界个改动",
        "recentchangeslinked-title": "搭“$1”有关个改动",
        "recentchangeslinked-summary": "箇页列出个是对链到某只指定页面个页面近段辰光个修订(或者是对指定分类个成员)。\n徕[[Special:Watchlist|你侬个关注表]]里个页用'''粗体'''显示。",
        "recentchangeslinked-page": "页面名称:",
        "undelete-search-submit": "搜尋",
        "namespace": "名字空间:",
        "invert": "反选择",
-       "tooltip-invert": "æ\89\93ä¸\8aæ\89\8eå\8b¾æ\9d¥å\9b¥è\84±é\80\89å®\9aå\90\8då­\97空é\97´ä¸ªæ\94¹å\8a¨ï¼\88å¦\82æ\9e\9cå\8b¾é\80\89æ\9c\89å\85³名字空间,箇么一道囥脱)",
-       "namespace_association": "æ\9c\89å\85³个名字空间",
+       "tooltip-invert": "æ\89\93ä¸\8aæ\89\8eå\8b¾æ\9d¥å\9b¥è\84±é\80\89å®\9aå\90\8då­\97空é\97´ä¸ªæ\94¹å\8a¨ï¼\88å¦\82æ\9e\9cå\8b¾é\80\89æ\90­ç\95\8c个名字空间,箇么一道囥脱)",
+       "namespace_association": "æ\90­ç\95\8c个名字空间",
        "tooltip-namespace_association": "打上扎勾来加上搭选定名字空间搭界个讨论或主题名字空间",
        "blanknamespace": "(主)",
        "contributions": "{{GENDER:$1|用户}}贡献",
        "year": "从箇年往前:",
        "sp-contributions-newbies": "只显示新用户个贡献",
        "sp-contributions-blocklog": "查封记录",
-       "sp-contributions-deleted": "删脱个用户贡献",
+       "sp-contributions-deleted": "删脱个{{GENDER:$1|用户}}贡献",
        "sp-contributions-talk": "讲张",
        "sp-contributions-search": "寻贡献记录",
        "sp-contributions-username": "IP地址要勿用户名:",
        "sp-contributions-toponly": "只显示阿末只版本个编辑",
        "sp-contributions-submit": "搜寻",
-       "whatlinkshere": "有啥链到箇里",
+       "whatlinkshere": "链进来点啥",
        "whatlinkshere-title": "链接到“$1”个页面",
        "whatlinkshere-page": "页面:",
        "linkshere": "下头个页链到[[:$1]]:",
-       "nolinkshere": "呒有页链到 '''[[:$1]]'''。",
+       "nolinkshere": "呒不页面链到<strong>[[:$1]]</strong>。",
        "isredirect": "转戳页",
        "istemplate": "包括",
        "isimage": "文件鏈接",
        "tooltip-ca-nstab-category": "望分类页",
        "tooltip-minoredit": "标作小编写",
        "tooltip-save": "保存侬个修改",
+       "tooltip-publish": "发布侬个改动",
        "tooltip-preview": "预览倷个更改。请勒拉保存前头用用俚。",
        "tooltip-diff": "显示侬对文本个修改",
        "tooltip-compareselectedversions": "查看本页面两只选定个修订版个差异。",
index 036c3e3..eb913d7 100644 (file)
        "passwordreset-emailelement": "באַניצער נאָמען: \n$1\n\nפראוויזארישער פּאַראָל: \n$2",
        "passwordreset-emailsentemail": "טאמער איז דער ע־פאסט אדרעס פארקניפט מיט אייער קאנטע, וועט מען שיקן א פאסווארט צוריקשטעלן ע-פּאָסט.",
        "passwordreset-emailsentusername": "טאמער איז פאראן אן ע־פאסט אדרעס פארקניפט מיט דעם באניצער־נאמען, וועט מען שיקן א פאסווארט צוריקשטעלן ע-פּאָסט.",
-       "passwordreset-emailsent-capture": "מען האט געשיקט א פאסווארט צוריקשטעלן בליצבריוו, וואס ווערט געוויזן אונטן.",
-       "passwordreset-emailerror-capture": "מען האט געשאפן א פאסווארט צוריקשטעלן בליצבריוו, וואס ווערט געוויזן אונטן, אבער שיקן צום {{GENDER:$2|באניצער}}איז דורכגעפאלן: $1",
        "passwordreset-nocaller": "מען דארף פֿארזארגן א רופֿער",
        "passwordreset-invalideamil": "אומגילטיקער ע־פאסט אדרעס",
        "changeemail": "ענדערן אדער אראפנעמען ע-פּאָסט אַדרעס",
        "changeemail-header": "דערגאַנצט די פֿאָרעם צו ענדערן אייער ע-פּאָסט אַדרעס .\nטאמער ווילט איר אראפנעמען די צוארדנונג פון איינעם פון אייערע ע־פאסט אדרעסן פו אייער קאנטע, לאזט ליידיג דעם נייעם ע־פאסט אדרעס ווען איר גיט איין די פֿארעם.",
-       "changeemail-passwordrequired": "איר וועט דארפן איינגעבן אייער פאסווארט צו באשטעטיגן די ענדערונג.",
        "changeemail-no-info": "איר דאַרפֿט זיין אַרײַנלאגירט צוצוקומען גלײַך צו דעם דאָזיגן בלאַט.",
        "changeemail-oldemail": "קראַנטער ע-פּאָסט אַדרעס:",
        "changeemail-newemail": "נײַער בליצפּאָסט אַדרעס:",
        "undo-nochange": "אויבערפלעכטלעך איז די רעדאקטירונג שוין געווארן אנולירט.",
        "undo-summary": "זיי מבטל רי-ווערסיע $1 פון [[Special:Contributions/$2|$2]] ([[User talk:$2|רעדן]])",
        "undo-summary-username-hidden": "זײַט מבטל ווערסיע $1 פון א באהאלטענעם באניצער",
-       "cantcreateaccounttitle": "מען קען נישט באשאפֿן קאנטע",
        "cantcreateaccount-text": "שאפֿן קאנטעס פון דעם IP אדרעס (<b>$1</b>) איז געווארן בלאקירט דורך [[User:$3|$3]]. די סיבה געגעבן פֿון $3 איז \"$2\".",
        "cantcreateaccount-range-text": "שאפן קאנטעס פון IP אדרעסן אינעם אפשטאנד <strong>$1</strong>, וואס נעמט אײַן אײַער IP אדרעס (<strong>$4</strong>), איז בלאקירט געווארן דורך [[User:$3|$3]].\n\nדער גרונט געגעבן פון $3 איז <em>$2</em>",
        "viewpagelogs": "װײַזן לאָג-ביכער פֿאַר דעם בלאַט",
index ba97b7c..907bb21 100644 (file)
        "nstab-template": "Àdàkọ",
        "nstab-help": "Ojúewé ìrànlọ́wọ́",
        "nstab-category": "Ẹ̀ka",
+       "mainpage-nstab": "Ojúewé Àkọ́kọ́",
        "nosuchaction": "Kò sí irú ìgbéṣe báun",
        "nosuchactiontext": "Ìgbéṣe tí URL yìí tọ́kasí kò tọ́.\nÓ ṣe é ṣe kó jẹ́ pé ẹ ṣe àṣìṣe URL ọ̀hún, tàbí kó jẹ́ pé ẹ tẹ̀lé ìjápọ̀ tí kò tọ́.\nÓ sì le jẹ́ pé kòkòrò wà nínú software tí {{SITENAME}} nlò.",
        "nosuchspecialpage": "Kò sí irú ojúewé pàtàkì báun",
        "passwordreset-emailtext-user": "Oníṣe $1 lórí {{SITENAME}} tọrọ àtúntò ọ̀rọ̀ìpamọ́ yín fùn {{SITENAME}} ($4). {{PLURAL:$3|Àkópamọ́|Àwọn àkópamọ́}} oníṣe ìsàlẹ̀ yìí ní ìbáṣe pọ̀ mọ́ àdírẹ̀sì e-mail yìí:\n\n$2\n\n{{PLURAL:$3|Ọ̀rọ̀ìpamọ́ onígbàdíẹ̀ yìí|Àwọn ọ̀rọ̀ìpamọ́ onígbàdíẹ̀ wọ̀nyí}} yíò dópin lẹ́yìn {{PLURAL:$5|ọjọ́ kan|ọjọ́ $5}}.\nẸ gbọ́dọ̀ lọ yan ọ̀rọ̀ìpamọ́ tuntun báyìí. Tóbá jẹ́ pé ẹ̀lòmíràn ló ṣe ìtọrọ yìí, tàbí tọ́bá jẹ́ pé ẹ ti rántí ọ̀rọ̀ìpamọ́ àtètèkọ́ṣe yín, tí ẹ kọ̀ sí fẹ́ yíipadà mọ́, ẹ lé ṣàìkàsí ìránṣẹ́ yìí, kí ẹ sì tẹ̀síwájú ní lo ọ̀rọ̀ìpamọ́ àtijọ́ yín.",
        "passwordreset-emailelement": "Orúkọ oníṣe: \n$1\n\nỌ̀rọ̀ìpamọ́ ìgbàdíẹ̀: \n$2",
        "passwordreset-emailsentemail": "E-mail àtúntò ọ̀rọ̀ìpamọ́ ti jẹ́ fífiránṣẹ́.",
-       "passwordreset-emailsent-capture": "E-mail àtúntò ọ̀rọ̀ìpamọ́ kan ti jẹ́ fífiránṣẹ́. Òhun nìyí nísàlẹ̀.",
-       "passwordreset-emailerror-capture": "E-mail ìyípadà ọ̀rọ̀ìpamọ́ jẹ́ dídá, òhun lóhàn nísàlẹ̀ yìí, sùgbọ́n ìfiránṣẹ́ rẹ̀ sí {{GENDER:$2|oníṣe}} náà kùnà: $1",
        "changeemail": "Ìyípadà àdírẹ̀sì E-mail",
        "changeemail-header": "Ìyípadà àdírẹ̀sì e-mail àkópamọ́",
        "changeemail-no-info": "Ẹ gbódọ̀ wọlé láti bósí ojúewé yìí tààrà.",
        "subject": "Orí ọ̀rọ̀/àkọlé:",
        "minoredit": "Àtúnṣe kékeré nìyí",
        "watchthis": "M'ójútó ojúewé yìí",
-       "savearticle": "Ìmúpamọ́ ojúewé",
+       "savearticle": "Ṣe àtẹ̀jáde ojú ewé",
+       "publishpage": "Ṣàtẹ̀jáde ojú ewé",
+       "publishchanges": "Ṣàtẹ̀jáde àtúnṣe",
        "preview": "Àyẹ̀wò",
        "showpreview": "Àkọ́yẹ̀wò",
        "showdiff": "Ìfihàn àwọn àtúnṣe",
        "undo-failure": "Àtúnṣe náà kò ṣe é múkúrò nítorí títakora àwọn àtúnṣe inú àrin.",
        "undo-norev": "Àtúnṣe náà kò ṣe é múkúrò nítorí pé kò sí tàbí pé ó ti jẹ́ píparẹ́.",
        "undo-summary": "Ìmúkúrò àtúnyẹ̀wò $1 ti [[Special:Contributions/$2|$2]] ([[User talk:$2|ọ̀rọ̀]])",
-       "cantcreateaccounttitle": "Ìforúkọsílẹ̀ kò se é se",
        "cantcreateaccount-text": "[[User:$3|$3]] ti dènà dídá àkópamọ́ láti orí àdírẹ́ẹ̀sì IP yìí ('''$1''').\n\nÌdí tí $3 ṣe ṣèyí ni ''$2''",
        "viewpagelogs": "Ẹ wo àkọsílẹ̀ ìṣẹ̀lẹ̀ fún ojúewé yìí",
        "nohistory": "Kò sí ìtàn àtùnṣe fún ojúewé yìí.",
        "shown-title": "{{PLURAL:$1|Ìfihàn èsì $1|Ìfihàn àwọn èsì $1}} nínú ojúewé kọ̀ọ̀kan",
        "viewprevnext": "Ẹ wo ($1 {{int:pipe-separator}} $2) ($3)",
        "searchmenu-exists": "'''Ojúewé tó ún jẹ́ \"[[:$1]]\" wà lórí wiki yìí'''",
-       "searchmenu-new": "'''Dá ojúewé \"[[:$1]]\" sí orí wiki yìí!'''",
+       "searchmenu-new": "<strong>Dá ojúewé \"[[:$1]]\" sí orí wiki yìí!</strong> {{PLURAL:$2|0=|Wo ojúewé tí a wá rí pẹ̀lú ìṣewárí rẹ.|Wo àwọn èsì ìṣewárí tí a rí.}}",
        "searchprofile-articles": "Àwọn ojúewé Àkóónú",
        "searchprofile-images": "Amóhùnmáwòrán",
        "searchprofile-everything": "Èyíkéyìí",
        "searchrelated": "tóbáramu",
        "searchall": "gbogbo",
        "showingresults": "Ìfihàn nísàlẹ̀ títí dé {{PLURAL:$1|èsì '''1'''|àwọn èsì '''$1'''}} láti ìbẹ̀rẹ̀ ní #'''$2'''.",
+       "search-showingresults": "{{PLURAL:$4|Èsì <strong>$1</strong> fún <strong>$3</strong>|Àwọn èsì <strong>$1 - $2</strong> fún <strong>$3</strong>}}",
        "search-nonefound": "Kò sí àwọn èsì kankan tóbáramu mọ́ ìtọrọ.",
        "powersearch-legend": "Àwárí kíkúnrẹ́rẹ́",
        "powersearch-ns": "Àwárí nínú orúkọàyè:",
        "search-external": "Àwárí lóde",
        "searchdisabled": "Ṣíṣàwárí nínú {{SITENAME}} wà ní dídálẹ́kun.\nNí báyìí ná ẹ le ṣàwárí lọ́dọ̀ Google.\nÀkíyèsí pé àwọn atọ́ka wọn fún àkóónú {{SITENAME}} le mọ́ jẹ́ tuntun.",
        "search-error": "Àṣìṣe ṣẹlẹ̀ fún ìwárí: $1",
-       "preferences": "Ã\80wá»\8dn Ã¬fẹÌ\81ràn",
+       "preferences": "Ã\80wá»\8dn Ã Ã yò",
        "mypreferences": "Àwọn ìfẹ́ràn",
        "prefs-edits": "Iye àwọn àtúnṣe:",
        "prefsnologintext2": "Ẹ jọ̀wọ́ ẹ $1 láti ṣe ìyípadà àwọn ìfẹ́ràn yín.",
        "tooltip-pt-logout": "Ìjáde",
        "tooltip-pt-createaccount": "Ó dára kí ẹ dá àkópamọ́ kí ẹ sì ṣe ìtẹ̀jáwọlé, ṣùgbọ́n kò pọn dandan",
        "tooltip-ca-talk": "Ìfọ̀rọ̀wérọ̀ nípa ohun inú ojúewé yìí",
-       "tooltip-ca-edit": "Ẹ le ṣe àtúnṣe sí ojúewé yìí.\nẸ jọ̀wọ́ ẹ lo bọtini àyẹ̀wò kí ẹ tó fipamọ́.",
+       "tooltip-ca-edit": "S'àtúnṣe ojúewé yi",
        "tooltip-ca-addsection": "Ẹ bẹ̀rẹ̀ abẹlẹ tuntun",
        "tooltip-ca-viewsource": "Àbò wà lórí ojúewé yìí.\nẸ le wo àmìọ̀rọ̀ rẹ̀.",
        "tooltip-ca-history": "Àwọn àtúnṣe tókọjá sí ojúewé yìí",
        "tooltip-t-recentchangeslinked": "Àwọn àtúnṣe tuntun nínú àwọn ojúewé tójápọ̀ láti inú ojúewé yìí",
        "tooltip-feed-rss": "RSS feed fùn ojúewé yìí",
        "tooltip-feed-atom": "Atom feed fún ojúewé yìí",
-       "tooltip-t-contributions": "Ẹ wo àkójọ àwọn àfikún oníṣe yìí",
+       "tooltip-t-contributions": "Àtòjọ àwọn àfikún {{GENDER:$1|oníṣe yìí}}",
        "tooltip-t-emailuser": "Ẹ fi e-mail ránṣẹ́ sí oníṣe yìí",
        "tooltip-t-upload": "Ìrùsókè àwọn fáìlì",
        "tooltip-t-specialpages": "Àkójọ gbogbo àwọn ojúewé pàtàkì",
        "tooltip-ca-nstab-main": "Ìfihàn inú ojúewé",
        "tooltip-ca-nstab-user": "Ẹ wo ojúewé oníṣe",
        "tooltip-ca-nstab-media": "Ẹ wò ojúewé amóhùnmáwòrán",
-       "tooltip-ca-nstab-special": "Ojúewé yìí ṣe pàtàkì, ẹ kò le è ṣ'àtúnṣe rẹ̀",
+       "tooltip-ca-nstab-special": "Ojúewé pàtàkì nì yí, kò le è ṣeẹ́túnṣe",
        "tooltip-ca-nstab-project": "Ẹ wo ojúewé iṣẹ́ọwọ́",
        "tooltip-ca-nstab-image": "Ẹ wo ojúewé faili",
        "tooltip-ca-nstab-mediawiki": "Iwo ìránṣẹ́ sístẹ́mù",
index 050a780..5a2986f 100644 (file)
        "passwordreset-emailtext-user": "{{SITENAME}}用戶$1請求更改閣下喺{{SITENAME}}道嘅密碼$4。同爾個電子郵件有關聯嘅用戶包括:\n\n$2\n\n{{PLURAL:$3|爾個|爾啲}}臨時密碼會喺{{$5}}日之後失效。\n\n如果係閣下自己請求改密碼嘅,請馬上登錄{{SITENAME}}並且更改密碼。如果閣下諗返起自己個密碼,或者根本無申請過改密碼嘅話,請忽略爾條訊息,繼續用返舊密碼。",
        "passwordreset-emailelement": "用戶名:\n$1\n\n臨時密碼:\n$2",
        "passwordreset-emailsentemail": "若果你個戶口有登記電郵,密碼重設電郵經已送出。",
-       "passwordreset-emailsent-capture": "密碼重設電郵經已送出,下面有顯示。",
-       "passwordreset-emailerror-capture": "密碼重設電郵經已送出,下面有顯示,但送畀{{GENDER:$2|user}}時失敗: $1",
        "changeemail": "改或者剷走電郵地址",
        "changeemail-header": "填好呢份表去改戶口電郵地址。若果你想剷走你戶口個電郵地址,填表時請將電郵地址欄留空。",
-       "changeemail-passwordrequired": "你要入密碼去確認改動。",
        "changeemail-no-info": "你一定要簽到咗去直接入來呢一版。",
        "changeemail-oldemail": "而家個電郵地址:",
        "changeemail-newemail": "新電郵地址:",
        "undo-nochange": "呢個編輯睇嚟經已一早取消咗。",
        "undo-summary": "取消由[[Special:Contributions/$2|$2]] ([[User talk:$2|對話]])所做嘅修訂 $1",
        "undo-summary-username-hidden": "取消匿埋咗嘅用戶嘅修改版本 $1",
-       "cantcreateaccounttitle": "唔可以開新戶口",
        "cantcreateaccount-text": "由呢個IP地址 ('''$1''') 開嘅新戶口已經被[[User:$3|$3]]封鎖。\n\n當中俾$3封鎖嘅原因係''$2''",
        "cantcreateaccount-range-text": "由呢個IP地址範圍<strong>$1</strong>(包括你個IP <strong>$4</strong>)開嘅新戶口已經畀[[User:$3|$3]]封鎖咗。\n\n$3畀嘅理由係<em>$2</em>",
        "viewpagelogs": "睇呢頁嘅日誌",
index f025e3e..1764b36 100644 (file)
        "history": "页面历史",
        "history_short": "历史",
        "updatedmarker": "更新于我上次访问后",
-       "printableversion": "打印版本",
+       "printableversion": "打印版本",
        "permalink": "固定链接",
        "print": "打印",
        "view": "查看",
        "passwordreset-emailelement": "用户名:\n$1\n\n临时密码:\n$2",
        "passwordreset-emailsentemail": "如果此邮件地址与您的账户相关联的话,将发送一封密码重置邮件。",
        "passwordreset-emailsentusername": "如果有邮件地址与此用户名相关联的话,将发送一封密码重置邮件。",
-       "passwordreset-emailsent-capture": "密码重设电子邮件已发送,并在下面显示。",
-       "passwordreset-emailerror-capture": "重置密码邮件已生成,但是无法向{{GENDER:$2|下列用户}} 发送:$1",
        "passwordreset-emailsent-capture2": "密码重置{{PLURAL:$1|邮件}}已发送。{{PLURAL:$1|用户名和密码|用户名和密码列表}}在下方显示。",
        "passwordreset-emailerror-capture2": "向{{GENDER:$2|用户}}发送电子邮件失败:$1 {{PLURAL:$3|用户名和密码|用户名和密码列表}}在下方显示。",
        "passwordreset-nocaller": "必须提供一个调用方",
        "passwordreset-nodata": "用户名和电子邮件地址均未提供",
        "changeemail": "更改或移除电子邮件地址",
        "changeemail-header": "完成此表格以更改您的电子邮件地址。如果您希望从您的账户中移除任何关联的电子邮件地址,请在提交表格时将新电子邮件地址留空。",
-       "changeemail-passwordrequired": "您需要输入您的密码以确认此次更改。",
        "changeemail-no-info": "\n您必须登录以直接访问本页。",
        "changeemail-oldemail": "当前电子邮件地址:",
        "changeemail-newemail": "新的电子邮件地址:",
        "undo-nochange": "这次编辑似乎已被撤销。",
        "undo-summary": "撤销[[Special:Contributions/$2|$2]]([[User talk:$2|讨论]])的版本$1",
        "undo-summary-username-hidden": "取消由一匿名用户所作的版本$1",
-       "cantcreateaccounttitle": "无法创建账户",
        "cantcreateaccount-text": "从该IP地址(<strong>$1</strong>)创建账户已被[[User:$3|$3]]禁止。\n\n$3的理由是<em>$2</em>",
        "cantcreateaccount-range-text": "从该IP地址段<strong>$1</strong>的账户创建已被[[User:$3|$3]]禁止,而这也包括了您的IP地址(<strong>$4</strong>)。\n\n$3给出的原因是<em>$2</em>",
        "viewpagelogs": "查看该页面的日志",
        "powersearch-togglenone": "全不选",
        "powersearch-remember": "记住选择用于以后的搜索",
        "search-external": "外部搜索",
-       "searchdisabled": "{{SITENAME}}的搜索已被禁用。您可以暂时使用搜索引擎进行搜索,须注意他们索引的{{SITENAME}}内容可能不是最新的。",
+       "searchdisabled": "{{SITENAME}}的搜索已被禁用。您可以暂时使用搜索引擎进行搜索,须注意索引的{{SITENAME}}内容可能不是最新的。",
        "search-error": "搜索时发生错误:$1",
        "preferences": "设置",
        "mypreferences": "参数设置",
        "uploadstash-errclear": "清除文件失败。",
        "uploadstash-refresh": "更新文件列表",
        "uploadstash-thumbnail": "显示缩略图",
+       "uploadstash-exception": "不能将上传内容存储至暂存处($1):“$2”。",
        "invalid-chunk-offset": "无效区块偏移量",
        "img-auth-accessdenied": "拒绝访问",
        "img-auth-nopathinfo": "PATH_INFO缺失。\n您的服务器尚未设置传送该信息。\n它可能基于CGI,因而不支持img_auth。\n请参见https://www.mediawiki.org/wiki/Special:MyLanguage/Manual:Image_Authorization。",
        "trackingcategories-disabled": "分类被禁用",
        "mailnologin": "无电子邮件地址",
        "mailnologintext": "您必须[[Special:UserLogin|登录]]并在您的[[Special:Preferences|系统设置]]中拥有有效的电子邮件地址才能向其他用户发送电子邮件。",
-       "emailuser": "ç\94µé\82®è\81\94ç³»",
+       "emailuser": "ç\94µé\82®è\81\94ç»\9cæ­¤ç\94¨æ\88·",
        "emailuser-title-target": "电邮联系该{{GENDER:$1|用户}}",
        "emailuser-title-notarget": "电邮联系",
        "emailpagetext": "您可以使用下面的表格发送电子邮件信息至该{{GENDER:$1|用户}}。您在[[Special:Preferences|系统设置]]中输入的电子邮件地址将显示为邮件的“发件人”地址,所以该用户将可以直接回复您。",
        "watchnologin": "未登录",
        "addwatch": "添加至监视列表",
        "addedwatchtext": "“[[:$1]]”及其讨论页已加入至您的[[Special:Watchlist|监视列表]]中。",
+       "addedwatchtext-talk": "“[[:$1]]”及其相关联页面已加入至您的[[Special:Watchlist|监视列表]]中。",
        "addedwatchtext-short": "页面“$1”已加入您的监视列表。",
        "removewatch": "从监视列表中删除",
        "removedwatchtext": "“[[:$1]]”及其讨论页已从您的[[Special:Watchlist|监视列表]]中移除。",
+       "removedwatchtext-talk": "“[[:$1]]”及其相关联页面已从您的[[Special:Watchlist|监视列表]]中移除。",
        "removedwatchtext-short": "页面“$1”已从您的监视列表移除。",
        "watch": "监视",
        "watchthispage": "监视本页",
        "undeletehistorynoadmin": "这个页面已被删除。删除原因显示在下方编辑摘要中,被删除前的所有版本文本连同删除前贡献用户的细节信息只对管理员可见。",
        "undelete-revision": "$1由$3(在$4 $5)所编写的已删除版本:",
        "undeleterevision-missing": "无效或丢失的版本。您可能使用了错误的链接,或者此版本已经被从存档中恢复或移除。",
+       "undeleterevision-duplicate-revid": "{{PLURAL:$1|$1个修订版本}}不能被恢复,因为{{PLURAL:$1|它|它们}}的<code>rev_id</code>已在使用中。",
        "undelete-nodiff": "找不到先前的版本。",
        "undeletebtn": "还原",
        "undeletelink": "查看/还原",
        "undeletedrevisions": "还原{{PLURAL:$1|$1个版本}}",
        "undeletedrevisions-files": "还原{{PLURAL:$1|$1个版本}}和{{PLURAL:$2|$2个文件}}",
        "undeletedfiles": "还原{{PLURAL:$1|$1个文件}}",
-       "cannotundelete": "恢复删除失败:\n$1",
+       "cannotundelete": "部分或全部还原删除失败:$1",
        "undeletedpage": "<strong>$1已经被还原</strong>\n\n最近的删除和还原记录请见[[Special:Log/delete|删除日志]]。",
        "undelete-header": "如要查询最近的记录请参阅[[Special:Log/delete|删除日志]]。",
        "undelete-search-title": "搜索已删除页面",
        "sp-contributions-newbies-sub": "新账户的贡献",
        "sp-contributions-newbies-title": "新账户的用户贡献",
        "sp-contributions-blocklog": "封禁日志",
-       "sp-contributions-suppresslog": "被隐藏的用户贡献",
-       "sp-contributions-deleted": "被删除的用户贡献",
+       "sp-contributions-suppresslog": "被屏蔽的{{GENDER:$1|用户}}贡献",
+       "sp-contributions-deleted": "被删除的{{GENDER:$1|用户}}贡献",
        "sp-contributions-uploads": "上传",
        "sp-contributions-logs": "日志",
        "sp-contributions-talk": "讨论",
        "sp-contributions-userrights": "用户权限管理",
-       "sp-contributions-blocked-notice": "è¿\99ä½\8dç\94¨æ\88·ç\8e°æ\97¶æ­£å\9c¨è¢«å°\81é\94\81中ã\80\82\næ\9c\80è¿\91ç\9a\84å°\81é\94\81æ\97¥å¿\97项ç\9b®å\9c¨ä¸\8bé\9d¢æ\8f\90ä¾\9b以便参考:",
-       "sp-contributions-blocked-notice-anon": "è¿\99个IPå\9c°å\9d\80ç\8e°æ\97¶æ­£å\9c¨è¢«å°\81é\94\81中ã\80\82\næ\9c\80è¿\91ç\9a\84å°\81é\94\81æ\97¥å¿\97项ç\9b®å\9c¨ä¸\8bé\9d¢æ\8f\90ä¾\9b以便参考:",
+       "sp-contributions-blocked-notice": "è¿\99ä½\8dç\94¨æ\88·ç\9b®å\89\8dæ­£å\9c¨è¢«å°\81ç¦\81ã\80\82æ\9c\80è¿\91ç\9a\84å°\81ç¦\81æ\97¥å¿\97è®°å½\95å\9c¨ä¸\8bé\9d¢æ\8f\90ä¾\9b以ä¾\9b参考:",
+       "sp-contributions-blocked-notice-anon": "è¿\99个IPå\9c°å\9d\80ç\9b®å\89\8dæ­£å\9c¨è¢«å°\81ç¦\81ã\80\82æ\9c\80è¿\91ç\9a\84å°\81ç¦\81æ\97¥å¿\97è®°å½\95å\9c¨ä¸\8bé\9d¢æ\8f\90ä¾\9b以ä¾\9b参考:",
        "sp-contributions-search": "搜索贡献",
        "sp-contributions-username": "IP地址或用户名:",
        "sp-contributions-toponly": "仅显示最后版本的编辑",
        "dberr-info": "(无法访问数据库:$1)",
        "dberr-info-hidden": "(无法访问数据库)",
        "dberr-usegoogle": "在此期间您可以尝试用 Google 来搜索。",
-       "dberr-outofdate": "须注意他们索引出来的内容可能不是最新的。",
+       "dberr-outofdate": "须注意索引出来的内容可能不是最新的。",
        "dberr-cachederror": "这是所请求页面的缓存副本,可能不是最新的。",
        "htmlform-invalid-input": "您输入的内容存在问题",
        "htmlform-select-badoption": "您指定的值不是有效选项。",
index 99518b6..e58564c 100644 (file)
        "passwordreset-emailelement": "使用者名稱:\n$1\n\n臨時密碼:\n$2",
        "passwordreset-emailsentemail": "若此確實為您帳號所登記的電子郵件地址,將會寄出重設密碼的信件給您。",
        "passwordreset-emailsentusername": "若此確實為您使用者名稱所登記的電子郵件地址,將會寄出重設密碼的信件給您。",
-       "passwordreset-emailsent-capture": "已寄出重設密碼的電子郵件,並於下方顯示。",
-       "passwordreset-emailerror-capture": "下列為重設密碼的電子郵件內容,傳送給{{GENDER:$2|使用者}}失敗:$1",
        "passwordreset-emailsent-capture2": "密碼重設{{PLURAL:$1|郵件|郵件}}已寄出,{{PLURAL:$1|使用者名稱與密碼|使用者名稱與密碼}}如下顯示。",
        "passwordreset-emailerror-capture2": "寄發電子郵件給{{GENDER:$2|使用者}}失敗:$1,{{PLURAL:$3|使用者名稱與密碼|使用者名稱與密碼}}如下顯示。",
        "passwordreset-nocaller": "必須提供 caller",
        "passwordreset-nodata": "未提供使用者名稱或是電子郵件地址",
        "changeemail": "變更或移除電子郵件地址",
        "changeemail-header": "請填寫此表單來變更您的電子郵件地址,若您想要移除您帳號所連結的所有電子郵件地址,請於新電子郵件地址欄位留空。",
-       "changeemail-passwordrequired": "您須要輸入您的密碼來確認此次變更。",
        "changeemail-no-info": "您必須登入方可直接存取此頁面。",
        "changeemail-oldemail": "目前的電子郵件地址:",
        "changeemail-newemail": "新的電子郵件地址:",
        "undo-nochange": "此編輯已被還原。",
        "undo-summary": "取消由 [[Special:Contributions/$2|$2]] ([[User talk:$2|對話]]) 所作出的修訂 $1",
        "undo-summary-username-hidden": "還原隱藏使用者的修訂 $1",
-       "cantcreateaccounttitle": "無法建立帳號",
        "cantcreateaccount-text": "自這個 IP 位址 (<strong>$1</strong>) 建立帳號已經被 [[User:$3|$3]] 封鎖。\n\n$3 封鎖的原因是 <em>$2</em>",
        "cantcreateaccount-range-text": "來自 IP 位址範圍 <strong>$1</strong>,包含您的 IP 位址 (<strong>$4</strong>) 所建立的帳號已經被 [[User:$3|$3]] 封鎖。\n\n$3 封鎖的原因是 <em>$2</em>",
        "viewpagelogs": "檢視此頁面的日誌",
        "sp-contributions-newbies-sub": "新帳號的貢獻",
        "sp-contributions-newbies-title": "新帳號的使用者貢獻",
        "sp-contributions-blocklog": "封鎖記錄",
-       "sp-contributions-suppresslog": "已禁止顯示的使用者貢獻",
-       "sp-contributions-deleted": "已刪除的使用者貢獻",
+       "sp-contributions-suppresslog": "已禁止顯示的{{GENDER:$1|使用者}}貢獻",
+       "sp-contributions-deleted": "已刪除的{{GENDER:$1|使用者}}貢獻",
        "sp-contributions-uploads": "上傳",
        "sp-contributions-logs": "日誌",
        "sp-contributions-talk": "對話",
index 7d79818..e778856 100644 (file)
@@ -8,6 +8,7 @@
  *
  */
 
+$fallback = 'sk';
 $fallback8bitEncoding = 'cp1250';
 
 $namespaceNames = [
index 299fd13..1fa701e 100644 (file)
@@ -33,6 +33,8 @@
  * @author לערי ריינהארט
  */
 
+$fallback = 'cs';
+
 $specialPageAliases = [
        'Activeusers'               => [ 'AktívniPoužívatelia' ],
        'Allmessages'               => [ 'VšetkySprávy' ],
diff --git a/maintenance/archives/patch-add-rc_name_type_patrolled_timestamp_index.sql b/maintenance/archives/patch-add-rc_name_type_patrolled_timestamp_index.sql
new file mode 100644 (file)
index 0000000..aa54e75
--- /dev/null
@@ -0,0 +1,2 @@
+-- @since 1.28
+CREATE INDEX /*i*/rc_name_type_patrolled_timestamp ON /*_*/recentchanges (rc_namespace, rc_type, rc_patrolled, rc_timestamp);
index a550d12..9fa6632 100644 (file)
@@ -41,8 +41,6 @@ class ChangePassword extends Maintenance {
        }
 
        public function execute() {
-               global $wgDisableAuthManager;
-
                if ( $this->hasOption( "user" ) ) {
                        $user = User::newFromName( $this->getOption( 'user' ) );
                } elseif ( $this->hasOption( "userid" ) ) {
@@ -55,17 +53,13 @@ class ChangePassword extends Maintenance {
                }
                $password = $this->getOption( 'password' );
                try {
-                       if ( $wgDisableAuthManager ) {
-                               $user->setPassword( $password );
-                       } else {
-                               $status = $user->changeAuthenticationData( [
-                                       'username' => $user->getName(),
-                                       'password' => $password,
-                                       'retype' => $password,
-                               ] );
-                               if ( !$status->isGood() ) {
-                                       throw new PasswordError( $status->getWikiText( null, null, 'en' ) );
-                               }
+                       $status = $user->changeAuthenticationData( [
+                               'username' => $user->getName(),
+                               'password' => $password,
+                               'retype' => $password,
+                       ] );
+                       if ( !$status->isGood() ) {
+                               throw new PasswordError( $status->getWikiText( null, null, 'en' ) );
                        }
                        $user->saveSettings();
                        $this->output( "Password set for " . $user->getName() . "\n" );
index e83d7c6..0554949 100644 (file)
@@ -66,7 +66,7 @@ class ConvertExtensionToRegistration extends Maintenance {
                $processor = new ReflectionClass( 'ExtensionProcessor' );
                $settings = $processor->getProperty( 'globalSettings' );
                $settings->setAccessible( true );
-               return $settings->getValue() + $this->formerGlobals;
+               return array_merge( $settings->getValue(), $this->formerGlobals );
        }
 
        public function execute() {
index 3591b9c..1872716 100644 (file)
@@ -56,8 +56,6 @@ class CreateAndPromote extends Maintenance {
        }
 
        public function execute() {
-               global $wgDisableAuthManager;
-
                $username = $this->getArg( 0 );
                $password = $this->getArg( 1 );
                $force = $this->hasOption( 'force' );
@@ -122,17 +120,13 @@ class CreateAndPromote extends Maintenance {
                if ( $password ) {
                        # Try to set the password
                        try {
-                               if ( $wgDisableAuthManager ) {
-                                       $user->setPassword( $password );
-                               } else {
-                                       $status = $user->changeAuthenticationData( [
-                                               'username' => $user->getName(),
-                                               'password' => $password,
-                                               'retype' => $password,
-                                       ] );
-                                       if ( !$status->isGood() ) {
-                                               throw new PasswordError( $status->getWikiText( null, null, 'en' ) );
-                                       }
+                               $status = $user->changeAuthenticationData( [
+                                       'username' => $user->getName(),
+                                       'password' => $password,
+                                       'retype' => $password,
+                               ] );
+                               if ( !$status->isGood() ) {
+                                       throw new PasswordError( $status->getWikiText( null, null, 'en' ) );
                                }
                                if ( $exists ) {
                                        $this->output( "Password set.\n" );
index c219b9b..50a4018 100644 (file)
@@ -32,8 +32,7 @@ class InitEditCount extends Maintenance {
                avoids locking tables or lagging slaves with large updates;
                calculates counts on a slave if possible.
 
-Background mode will be automatically used if the server is MySQL 4.0
-(which does not support subqueries) or if multiple servers are listed
+Background mode will be automatically used if multiple servers are listed
 in the load balancer, usually indicating a replication environment.' );
                $this->addDescription( 'Batch-recalculate user_editcount fields from the revision table' );
        }
@@ -46,13 +45,12 @@ in the load balancer, usually indicating a replication environment.' );
                $dbver = $dbw->getServerVersion();
 
                // Autodetect mode...
-               $backgroundMode = wfGetLB()->getServerCount() > 1 ||
-                       ( $dbw instanceof DatabaseMysql );
-
                if ( $this->hasOption( 'background' ) ) {
                        $backgroundMode = true;
                } elseif ( $this->hasOption( 'quick' ) ) {
                        $backgroundMode = false;
+               } else {
+                       $backgroundMode = wfGetLB()->getServerCount() > 1;
                }
 
                if ( $backgroundMode ) {
@@ -96,7 +94,6 @@ in the load balancer, usually indicating a replication environment.' );
                                wfWaitForSlaves();
                        }
                } else {
-                       // Subselect should work on modern MySQLs etc
                        $this->output( "Using single-query mode...\n" );
                        $sql = "UPDATE $user SET user_editcount=(SELECT COUNT(*) FROM $revision WHERE rev_user=user_id)";
                        $dbw->query( $sql );
index 48b2250..ea087a6 100644 (file)
@@ -861,6 +861,7 @@ CREATE INDEX /*i*/new_name_timestamp ON /*_*/recentchanges (rc_new,rc_namespace,
 CREATE INDEX /*i*/rc_ip ON /*_*/recentchanges (rc_ip);
 CREATE INDEX /*i*/rc_ns_usertext ON /*_*/recentchanges (rc_namespace, rc_user_text);
 CREATE INDEX /*i*/rc_user_text ON /*_*/recentchanges (rc_user_text, rc_timestamp);
+CREATE INDEX /*i*/rc_name_type_patrolled_timestamp ON /*_*/recentchanges (rc_namespace, rc_type, rc_patrolled, rc_timestamp);
 
 
 CREATE TABLE /*_*/watchlist (
diff --git a/maintenance/oracle/archives/patch-add-rc_name_type_patrolled_timestamp_index.sql b/maintenance/oracle/archives/patch-add-rc_name_type_patrolled_timestamp_index.sql
new file mode 100644 (file)
index 0000000..cd0d396
--- /dev/null
@@ -0,0 +1,4 @@
+define mw_prefix='{$wgDBprefix}';
+
+CREATE INDEX &mw_prefix.recentchanges_i08 ON &mw_prefix.recentchanges (rc_namespace, rc_type, rc_patrolled, rc_timestamp);
+
index 27c3030..d9369c9 100644 (file)
@@ -434,6 +434,7 @@ CREATE INDEX &mw_prefix.recentchanges_i04 ON &mw_prefix.recentchanges (rc_new,rc
 CREATE INDEX &mw_prefix.recentchanges_i05 ON &mw_prefix.recentchanges (rc_ip);
 CREATE INDEX &mw_prefix.recentchanges_i06 ON &mw_prefix.recentchanges (rc_namespace, rc_user_text);
 CREATE INDEX &mw_prefix.recentchanges_i07 ON &mw_prefix.recentchanges (rc_user_text, rc_timestamp);
+CREATE INDEX &mw_prefix.recentchanges_i08 ON &mw_prefix.recentchanges (rc_namespace, rc_type, rc_patrolled, rc_timestamp);
 
 CREATE TABLE &mw_prefix.watchlist (
   wl_id                     NUMBER     NOT NULL,
index 61cb198..95c87c0 100644 (file)
@@ -446,6 +446,7 @@ CREATE INDEX rc_namespace_title ON recentchanges (rc_namespace, rc_title);
 CREATE INDEX rc_cur_id          ON recentchanges (rc_cur_id);
 CREATE INDEX new_name_timestamp ON recentchanges (rc_new, rc_namespace, rc_timestamp);
 CREATE INDEX rc_ip              ON recentchanges (rc_ip);
+CREATE INDEX rc_name_type_patrolled_timestamp ON recentchanges (rc_namespace, rc_type, rc_patrolled, rc_timestamp);
 
 
 CREATE SEQUENCE watchlist_wl_id_seq;
index 5b035e1..70a26cb 100644 (file)
@@ -164,8 +164,12 @@ class PurgeChangedFiles extends Maintenance {
                                        continue;
                                }
 
-                               // Purge current version and any versions in oldimage table
+                               // Purge current version and its thumbnails
                                $file->purgeCache();
+                               // Purge the old versions and their thumbnails
+                               foreach ( $file->getHistory() as $oldFile ) {
+                                       $oldFile->purgeCache();
+                               }
 
                                if ( $logType === 'delete' ) {
                                        // If there is an orphaned storage file... delete it
index 0ea52ca..94335cf 100644 (file)
@@ -57,10 +57,8 @@ class FixBug20757 extends Maintenance {
 
                $totalRevs = $dbr->selectField( 'text', 'MAX(old_id)', false, __METHOD__ );
 
-               if ( $dbr->getType() == 'mysql' ) {
-                       // In MySQL 4.1+, the binary field old_text has a non-working LOWER() function
-                       $lowerLeft = 'LOWER(CONVERT(LEFT(old_text,22) USING latin1))';
-               }
+               // In MySQL 4.1+, the binary field old_text has a non-working LOWER() function
+               $lowerLeft = 'LOWER(CONVERT(LEFT(old_text,22) USING latin1))';
 
                while ( true ) {
                        print "ID: $startId / $totalRevs\r";
index 9c9bdfb..40506bf 100644 (file)
@@ -1136,6 +1136,7 @@ CREATE INDEX /*i*/new_name_timestamp ON /*_*/recentchanges (rc_new,rc_namespace,
 CREATE INDEX /*i*/rc_ip ON /*_*/recentchanges (rc_ip);
 CREATE INDEX /*i*/rc_ns_usertext ON /*_*/recentchanges (rc_namespace, rc_user_text);
 CREATE INDEX /*i*/rc_user_text ON /*_*/recentchanges (rc_user_text, rc_timestamp);
+CREATE INDEX /*i*/rc_name_type_patrolled_timestamp ON /*_*/recentchanges (rc_namespace, rc_type, rc_patrolled, rc_timestamp);
 
 
 CREATE TABLE /*_*/watchlist (
index 0d8d39f..0d8cfd6 100644 (file)
@@ -333,6 +333,9 @@ return [
                'targets' => [ 'desktop', 'mobile' ],
        ],
        'jquery.jStorage' => [
+               'deprecated' => [
+                       'message' => 'Please use "mediawiki.storage" instead.',
+               ],
                'scripts' => 'resources/lib/jquery/jquery.jStorage.js',
                'dependencies' => 'json',
        ],
@@ -370,6 +373,7 @@ return [
        /* jQuery Tipsy */
 
        'jquery.tipsy' => [
+               'deprecated' => true,
                'scripts' => 'resources/src/jquery.tipsy/jquery.tipsy.js',
                'styles' => 'resources/src/jquery.tipsy/jquery.tipsy.css',
        ],
@@ -377,6 +381,9 @@ return [
        /* jQuery UI */
 
        'jquery.ui.core' => [
+               'deprecated' => [
+                       'message' => 'Please use "mediawiki.ui.button" or "oojs-ui" instead.',
+               ],
                'scripts' => 'resources/lib/jquery.ui/jquery.ui.core.js',
                'dependencies' => [
                        'jquery.ui.core.styles',
@@ -655,11 +662,13 @@ return [
                'group' => 'jquery.ui',
        ],
        'jquery.ui.widget' => [
+               'deprecated' => true,
                'scripts' => 'resources/lib/jquery.ui/jquery.ui.widget.js',
                'group' => 'jquery.ui',
        ],
        // Effects
        'jquery.effects.core' => [
+               'deprecated' => true,
                'scripts' => 'resources/lib/jquery.ui/jquery.ui.effect.js',
                'group' => 'jquery.ui',
        ],
@@ -923,6 +932,7 @@ return [
                        'mediawiki.api.edit',
                        'json',
                ],
+               'targets' => [ 'desktop', 'mobile' ],
        ],
        'mediawiki.api.user' => [
                'scripts' => 'resources/src/mediawiki/api/user.js',
@@ -1706,14 +1716,6 @@ return [
                'position' => 'top',
                'targets' => [ 'desktop', 'mobile' ],
        ],
-       'mediawiki.page.patrol' => [
-               'position' => 'top',
-               'styles' => [
-                       'resources/src/mediawiki/page/mediawiki.page.patrol.css',
-                       'resources/src/mediawiki/page/mediawiki.page.patrol.print.css'
-                               => [ 'media' => 'print' ],
-               ]
-       ],
        'mediawiki.page.patrol.ajax' => [
                'scripts' => 'resources/src/mediawiki/page/patrol.ajax.js',
                'dependencies' => [
index 50bfa87..62be0d8 100644 (file)
                        for ( key in ts.collationTable ) {
                                // Check hasOwn to be safe
                                if ( ts.collationTable.hasOwnProperty( key ) ) {
-                                       keys.push( key );
+                                       keys.push( mw.RegExp.escape( key ) );
                                }
                        }
                        if ( keys.length ) {
-                               ts.collationRegex = new RegExp( '[' + keys.join( '' ) + ']', 'ig' );
+                               ts.collationRegex = new RegExp( keys.join( '|' ), 'ig' );
                        }
                }
        }
index 07c7d76..6c63957 100644 (file)
@@ -9,7 +9,11 @@
        $( function () {
                var idleTimeout = 3000,
                        api = new mw.Api(),
-                       pending = null,
+                       timer,
+                       pending,
+                       lastText,
+                       lastSummary,
+                       lastTextHash,
                        $form = $( '#editform' ),
                        $text = $form.find( '#wpTextbox1' ),
                        $summary = $form.find( '#wpSummary' ),
                        model = $form.find( '[name=model]' ).val(),
                        format = $form.find( '[name=format]' ).val(),
                        revId = $form.find( '[name=parentRevId]' ).val(),
-                       lastText = $text.textSelection( 'getContents' ),
-                       timer = null;
+                       lastPriority = 0,
+                       PRIORITY_LOW = 1,
+                       PRIORITY_HIGH = 2;
 
                // Send a request to stash the edit to the API.
                // If a request is in progress, abort it since its payload is stale and the API
                // may limit concurrent stash parses.
                function stashEdit() {
-                       if ( pending ) {
-                               pending.abort();
-                       }
-
                        api.getToken( 'csrf' ).then( function ( token ) {
-                               lastText = $text.textSelection( 'getContents' );
+                               var req, params,
+                                       textChanged = isTextChanged(),
+                                       priority = textChanged ? PRIORITY_HIGH : PRIORITY_LOW;
+
+                               if ( pending ) {
+                                       if ( lastPriority > priority ) {
+                                               // Stash request for summary change should wait on pending text change stash
+                                               pending.then( checkStash );
+                                               return;
+                                       }
+                                       pending.abort();
+                               }
 
-                               pending = api.post( {
+                               // Update the "last" tracking variables
+                               lastSummary = $summary.textSelection( 'getContents' );
+                               lastPriority = priority;
+                               if ( textChanged ) {
+                                       lastText = $text.textSelection( 'getContents' );
+                                       // Reset hash
+                                       lastTextHash = null;
+                               }
+
+                               params = {
                                        action: 'stashedit',
                                        token: token,
                                        title: mw.config.get( 'wgPageName' ),
                                        section: section,
                                        sectiontitle: '',
-                                       text: lastText,
-                                       summary: $summary.textSelection( 'getContents' ),
+                                       summary: lastSummary,
                                        contentmodel: model,
                                        contentformat: format,
                                        baserevid: revId
+                               };
+                               if ( lastTextHash ) {
+                                       params.stashedtexthash = lastTextHash;
+                               } else {
+                                       params.text = lastText;
+                               }
+
+                               req = api.post( params );
+                               pending = req;
+                               req.then( function ( data ) {
+                                       if ( req === pending ) {
+                                               pending = null;
+                                       }
+                                       if ( data.stashedit && data.stashedit.texthash ) {
+                                               lastTextHash = data.stashedit.texthash;
+                                       } else {
+                                               // Request failed or text hash expired;
+                                               // include the text in a future stash request.
+                                               lastTextHash = null;
+                                       }
                                } );
                        } );
                }
 
-               // Check if edit body text changed since the last stashEdit() call or if no edit
-               // stash calls have yet been made
-               function isChanged() {
-                       var newText = $text.textSelection( 'getContents' );
-                       return newText !== lastText;
+               // Whether the body text content changed since the last stashEdit()
+               function isTextChanged() {
+                       return lastText !== $text.textSelection( 'getContents' );
+               }
+
+               // Whether the edit summary has changed since the last stashEdit()
+               function isSummaryChanged() {
+                       return lastSummary !== $summary.textSelection( 'getContents' );
                }
 
-               function onEditorIdle() {
-                       if ( !isChanged() ) {
+               // Check whether text or summary have changed and call stashEdit()
+               function checkStash() {
+                       if ( !isTextChanged() && !isSummaryChanged() ) {
                                return;
                        }
 
                        stashEdit();
                }
 
-               function onTextKeyUp( e ) {
+               function onKeyUp( e ) {
                        // Ignore keystrokes that don't modify text, like cursor movements.
                        // See <http://www.javascripter.net/faq/keycodes.htm> and
                        // <http://www.quirksmode.org/js/keys.html>. We don't have to be exhaustive,
                        }
 
                        clearTimeout( timer );
-                       timer = setTimeout( onEditorIdle, idleTimeout );
+                       timer = setTimeout( checkStash, idleTimeout );
+               }
+
+               function onSummaryFocus() {
+                       // Summary typing is usually near the end of the workflow and involves less pausing.
+                       // Re-stash more frequently in hopes of capturing the final summary before submission.
+                       idleTimeout = 1000;
+                       // Stash now since the text is likely the final version. The re-stashes based on the
+                       // summary are targeted at caching edit checks that need the final summary.
+                       checkStash();
+               }
+
+               function onTextFocus() {
+                       // User returned to the text field... reset stash rate to default
+                       idleTimeout = 3000;
                }
 
                function onFormLoaded() {
                                // probably save the page soon
                                || $.inArray( $form.find( '#mw-edit-mode' ).val(), [ 'preview', 'diff' ] ) > -1
                        ) {
-                               stashEdit();
+                               checkStash();
                        }
                }
 
-               // We don't attempt to stash new section edits because in such cases
-               // the parser output varies on the edit summary (since it determines
-               // the new section's name).
+               // We don't attempt to stash new section edits because in such cases the parser output
+               // varies on the edit summary (since it determines the new section's name).
                if ( $form.find( 'input[name=wpSection]' ).val() === 'new' ) {
                        return;
                }
 
-               $text.on( { change: onEditorIdle, keyup: onTextKeyUp } );
-               $summary.on( { focus: onEditorIdle } );
+               $text.on( {
+                       change: checkStash,
+                       keyup: onKeyUp,
+                       focus: onTextFocus
+               } );
+               $summary.on( {
+                       focus: onSummaryFocus,
+                       focusout: checkStash,
+                       keyup: onKeyUp
+               } );
                onFormLoaded();
-
        } );
 }( mediaWiki, jQuery ) );
index 6a7c76a..d387a2d 100644 (file)
@@ -19,6 +19,7 @@ div#column-one,
 #footer-places,
 .mw-hidden-catlinks,
 .usermessage,
+.patrollink,
 .ns-0 .mw-redirectedfrom,
 div.magnify,
 #mw-navigation,
index 786f53d..7ccf59e 100644 (file)
@@ -289,6 +289,11 @@ table.small {
        font-style: italic;
 }
 
+span.unpatrolled {
+       font-weight: bold;
+       color: #f00;
+}
+
 div.gallerybox {
        width: 150px;
 }
index 38d2a27..de442e9 100644 (file)
@@ -115,6 +115,23 @@ span.history-deleted {
        font-style: italic;
 }
 
+/**
+ * Patrol stuff
+ */
+.not-patrolled {
+       background-color: #ffa;
+}
+
+.unpatrolled {
+       font-weight: bold;
+       color: #f00;
+}
+
+div.patrollink {
+       font-size: 75%;
+       text-align: right;
+}
+
 /**
  * Forms
  */
index ef4f6df..11784fb 100644 (file)
                                 * The reason css strings are not concatenated anymore is bug 31676. We now check
                                 * whether it's safe to extend the stylesheet.
                                 *
+                                * @protected
                                 * @param {Object} [messages] List of key/value pairs to be added to mw#messages.
                                 * @param {Object} [templates] List of key/value pairs to be added to mw#templates.
                                 */
                                 *         OO.compare( [ 1 ], [ 1 ] );
                                 *     } );
                                 *
+                                * Since MediaWiki 1.23 this also returns a promise.
+                                *
+                                * Since MediaWiki 1.28 the promise is resolved with a `require` function.
+                                *
                                 * @param {string|Array} dependencies Module name or array of modules names the
                                 *  callback depends on to be ready before executing
                                 * @param {Function} [ready] Callback to execute when all dependencies are ready
                                 * @param {Function} [error] Callback to execute if one or more dependencies failed
-                                * @return {jQuery.Promise}
-                                * @since 1.23 this returns a promise
+                                * @return {jQuery.Promise} With a `require` function
                                 */
                                using: function ( dependencies, ready, error ) {
                                        var deferred = $.Deferred();
                                        dependencies = resolve( dependencies );
                                        if ( allReady( dependencies ) ) {
                                                // Run ready immediately
-                                               deferred.resolve();
+                                               deferred.resolve( mw.loader.require );
                                        } else if ( anyFailed( dependencies ) ) {
                                                // Execute error immediately if any dependencies have errors
                                                deferred.reject(
                                                );
                                        } else {
                                                // Not all dependencies are ready: queue up a request
-                                               request( dependencies, deferred.resolve, deferred.reject );
+                                               request( dependencies, function () {
+                                                       deferred.resolve( mw.loader.require );
+                                               }, deferred.reject );
                                        }
 
                                        return deferred.promise();
                                 *
                                 * @protected
                                 * @since 1.27
-                                * @return {Array}
                                 */
                                require: function ( moduleName ) {
                                        var state = mw.loader.getState( moduleName );
diff --git a/resources/src/mediawiki/page/mediawiki.page.patrol.css b/resources/src/mediawiki/page/mediawiki.page.patrol.css
deleted file mode 100644 (file)
index f237dbd..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-.not-patrolled {
-       background-color: #ffa;
-}
-
-.unpatrolled {
-       font-weight: bold;
-       color: #f00;
-}
-
-.patrollink {
-       font-size: 75%;
-       text-align: right;
-}
diff --git a/resources/src/mediawiki/page/mediawiki.page.patrol.print.css b/resources/src/mediawiki/page/mediawiki.page.patrol.print.css
deleted file mode 100644 (file)
index 497bceb..0000000
+++ /dev/null
@@ -1,3 +0,0 @@
-.patrollink {
-       display: none;
-}
index 62ee94e..d026cb0 100644 (file)
@@ -77,7 +77,7 @@ function isCompatible( str ) {
        var NORLQ, script;
        if ( !isCompatible() ) {
                // Undo class swapping in case of an unsupported browser.
-               // See OutputPage::getHeadScripts().
+               // See ResourceLoaderClientHtml::getDocumentAttributes().
                document.documentElement.className = document.documentElement.className
                        .replace( /(^|\s)client-js(\s|$)/, '$1client-nojs$2' );
 
index 85bf954..84bf2fd 100644 (file)
@@ -64,10 +64,13 @@ class ResourceLoaderTestModule extends ResourceLoaderModule {
        protected $dependencies = [];
        protected $group = null;
        protected $source = 'local';
+       protected $position = 'bottom';
        protected $script = '';
        protected $styles = '';
        protected $skipFunction = null;
        protected $isRaw = false;
+       protected $isKnownEmpty = false;
+       protected $type = ResourceLoaderModule::LOAD_GENERAL;
        protected $targets = [ 'phpunit' ];
 
        public function __construct( $options = [] ) {
@@ -99,6 +102,13 @@ class ResourceLoaderTestModule extends ResourceLoaderModule {
        public function getSource() {
                return $this->source;
        }
+       public function getPosition() {
+               return $this->position;
+       }
+
+       public function getType() {
+               return $this->type;
+       }
 
        public function getSkipFunction() {
                return $this->skipFunction;
@@ -107,6 +117,9 @@ class ResourceLoaderTestModule extends ResourceLoaderModule {
        public function isRaw() {
                return $this->isRaw;
        }
+       public function isKnownEmpty( ResourceLoaderContext $context ) {
+               return $this->isKnownEmpty;
+       }
 
        public function enableModuleContentVersion() {
                return true;
index 9934749..c637d34 100644 (file)
@@ -139,72 +139,35 @@ class OutputPageTest extends MediaWikiTestCase {
        public static function provideMakeResourceLoaderLink() {
                // @codingStandardsIgnoreStart Generic.Files.LineLength
                return [
-                       // Load module script only
+                       // Single only=scripts load
                        [
                                [ 'test.foo', ResourceLoaderModule::TYPE_SCRIPTS ],
                                "<script>(window.RLQ=window.RLQ||[]).push(function(){"
                                        . 'mw.loader.load("http://127.0.0.1:8080/w/load.php?debug=false\u0026lang=en\u0026modules=test.foo\u0026only=scripts\u0026skin=fallback");'
                                        . "});</script>"
                        ],
-                       [
-                               // Don't condition wrap raw modules (like the startup module)
-                               [ 'test.raw', ResourceLoaderModule::TYPE_SCRIPTS ],
-                               '<script async="" src="http://127.0.0.1:8080/w/load.php?debug=false&amp;lang=en&amp;modules=test.raw&amp;only=scripts&amp;skin=fallback"></script>'
-                       ],
-                       // Load module styles only
-                       // This also tests the order the modules are put into the url
+                       // Multiple only=styles load
                        [
                                [ [ 'test.baz', 'test.foo', 'test.bar' ], ResourceLoaderModule::TYPE_STYLES ],
 
                                '<link rel="stylesheet" href="http://127.0.0.1:8080/w/load.php?debug=false&amp;lang=en&amp;modules=test.bar%2Cbaz%2Cfoo&amp;only=styles&amp;skin=fallback"/>'
                        ],
-                       // Load private module (only=scripts)
+                       // Private embed (only=scripts)
                        [
                                [ 'test.quux', ResourceLoaderModule::TYPE_SCRIPTS ],
                                "<script>(window.RLQ=window.RLQ||[]).push(function(){"
                                        . "mw.test.baz({token:123});mw.loader.state({\"test.quux\":\"ready\"});"
                                        . "});</script>"
                        ],
-                       // Load private module (combined)
-                       [
-                               [ 'test.quux', ResourceLoaderModule::TYPE_COMBINED ],
-                               "<script>(window.RLQ=window.RLQ||[]).push(function(){"
-                                       . "mw.loader.implement(\"test.quux\",function($,jQuery,require,module){"
-                                       . "mw.test.baz({token:123});},{\"css\":[\".mw-icon{transition:none}"
-                                       . "\"]});});</script>"
-                       ],
-                       // Load no modules
-                       [
-                               [ [], ResourceLoaderModule::TYPE_COMBINED ],
-                               '',
-                       ],
-                       // noscript group
-                       [
-                               [ 'test.noscript', ResourceLoaderModule::TYPE_STYLES ],
-                               '<noscript><link rel="stylesheet" href="http://127.0.0.1:8080/w/load.php?debug=false&amp;lang=en&amp;modules=test.noscript&amp;only=styles&amp;skin=fallback"/></noscript>'
-                       ],
-                       // Load two modules in separate groups
-                       [
-                               [ [ 'test.group.foo', 'test.group.bar' ], ResourceLoaderModule::TYPE_COMBINED ],
-                               "<script>(window.RLQ=window.RLQ||[]).push(function(){"
-                                       . 'mw.loader.load("http://127.0.0.1:8080/w/load.php?debug=false\u0026lang=en\u0026modules=test.group.bar\u0026skin=fallback");'
-                                       . "});</script>\n"
-                                       . "<script>(window.RLQ=window.RLQ||[]).push(function(){"
-                                       . 'mw.loader.load("http://127.0.0.1:8080/w/load.php?debug=false\u0026lang=en\u0026modules=test.group.foo\u0026skin=fallback");'
-                                       . "});</script>"
-                       ],
                ];
                // @codingStandardsIgnoreEnd
        }
 
        /**
+        * See ResourceLoaderClientHtmlTest for full coverage.
+        *
         * @dataProvider provideMakeResourceLoaderLink
         * @covers OutputPage::makeResourceLoaderLink
-        * @covers ResourceLoader::makeLoaderImplementScript
-        * @covers ResourceLoader::makeModuleResponse
-        * @covers ResourceLoader::makeInlineScript
-        * @covers ResourceLoader::makeLoaderStateScript
-        * @covers ResourceLoader::createLoaderURL
         */
        public function testMakeResourceLoaderLink( $args, $expectedHtml ) {
                $this->setMwGlobals( [
@@ -238,25 +201,9 @@ class OutputPageTest extends MediaWikiTestCase {
                                'styles' => '/* pref-animate=off */ .mw-icon { transition: none; }',
                                'group' => 'private',
                        ] ),
-                       'test.raw' => new ResourceLoaderTestModule( [
-                               'script' => 'mw.test.baz( { token: 123 } );',
-                               'isRaw' => true,
-                       ] ),
-                       'test.noscript' => new ResourceLoaderTestModule( [
-                               'styles' => '.mw-test-noscript { content: "style"; }',
-                               'group' => 'noscript',
-                       ] ),
-                       'test.group.bar' => new ResourceLoaderTestModule( [
-                               'styles' => '.mw-group-bar { content: "style"; }',
-                               'group' => 'bar',
-                       ] ),
-                       'test.group.foo' => new ResourceLoaderTestModule( [
-                               'styles' => '.mw-group-foo { content: "style"; }',
-                               'group' => 'foo',
-                       ] ),
                ] );
                $links = $method->invokeArgs( $out, $args );
-               $actualHtml = implode( "\n", $links['html'] );
+               $actualHtml = strval( $links );
                $this->assertEquals( $expectedHtml, $actualHtml );
        }
 
index 155a9dd..487ab84 100644 (file)
@@ -13,8 +13,6 @@ class ApiLoginTest extends ApiTestCase {
         * Test result of attempted login with an empty username
         */
        public function testApiLoginNoName() {
-               global $wgDisableAuthManager;
-
                $session = [
                        'wsTokenSecrets' => [ 'login' => 'foobar' ],
                ];
@@ -22,11 +20,11 @@ class ApiLoginTest extends ApiTestCase {
                        'lgname' => '', 'lgpassword' => self::$users['sysop']->getPassword(),
                        'lgtoken' => (string)( new MediaWiki\Session\Token( 'foobar', '' ) )
                ], $session );
-               $this->assertEquals( $wgDisableAuthManager ? 'NoName' : 'Failed', $data[0]['login']['result'] );
+               $this->assertEquals( 'Failed', $data[0]['login']['result'] );
        }
 
        public function testApiLoginBadPass() {
-               global $wgServer, $wgDisableAuthManager;
+               global $wgServer;
 
                $user = self::$users['sysop'];
                $userName = $user->getUser()->getName();
@@ -64,7 +62,7 @@ class ApiLoginTest extends ApiTestCase {
                $this->assertNotInternalType( "bool", $result );
                $a = $result["login"]["result"];
 
-               $this->assertEquals( $wgDisableAuthManager ? 'WrongPass' : 'Failed', $a );
+               $this->assertEquals( 'Failed', $a );
        }
 
        public function testApiLoginGoodPass() {
index ac4d2c9..7e1f9d8 100644 (file)
@@ -9,7 +9,7 @@ abstract class ApiTestCase extends MediaWikiLangTestCase {
        protected $apiContext;
 
        protected function setUp() {
-               global $wgServer, $wgDisableAuthManager;
+               global $wgServer;
 
                parent::setUp();
                self::$apiUrl = $wgServer . wfScript( 'api' );
@@ -22,7 +22,7 @@ abstract class ApiTestCase extends MediaWikiLangTestCase {
                ];
 
                $this->setMwGlobals( [
-                       'wgAuth' => $wgDisableAuthManager ? new AuthPlugin : new MediaWiki\Auth\AuthManagerAuthPlugin,
+                       'wgAuth' => new MediaWiki\Auth\AuthManagerAuthPlugin,
                        'wgRequest' => new FauxRequest( [] ),
                        'wgUser' => self::$users['sysop']->getUser(),
                ] );
index 1ded0df..89e48f7 100644 (file)
@@ -7,15 +7,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\AbstractAuthenticationProvider
  */
 class AbstractAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        public function testAbstractAuthenticationProvider() {
                $provider = $this->getMockForAbstractClass( AbstractAuthenticationProvider::class );
                $providerPriv = \TestingAccessWrapper::newFromObject( $provider );
index ecce932..a1cdf7e 100644 (file)
@@ -7,15 +7,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\AbstractPasswordPrimaryAuthenticationProvider
  */
 class AbstractPasswordPrimaryAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        public function testConstructor() {
                $provider = $this->getMockForAbstractClass(
                        AbstractPasswordPrimaryAuthenticationProvider::class
index c35430e..9638451 100644 (file)
@@ -7,15 +7,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\AbstractPreAuthenticationProvider
  */
 class AbstractPreAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        public function testAbstractPreAuthenticationProvider() {
                $user = \User::newFromName( 'UTSysop' );
 
index 420a330..d8588d5 100644 (file)
@@ -7,15 +7,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\AbstractPrimaryAuthenticationProvider
  */
 class AbstractPrimaryAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        public function testAbstractPrimaryAuthenticationProvider() {
                $user = \User::newFromName( 'UTSysop' );
 
index 9cdc051..bb90dd9 100644 (file)
@@ -7,15 +7,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\AbstractSecondaryAuthenticationProvider
  */
 class AbstractSecondaryAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        public function testAbstractSecondaryAuthenticationProvider() {
                $user = \User::newFromName( 'UTSysop' );
 
index 82608b0..99b9029 100644 (file)
@@ -30,12 +30,7 @@ class AuthManagerTest extends \MediaWikiTestCase {
        protected $managerPriv;
 
        protected function setUp() {
-               global $wgDisableAuthManager;
-
                parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
 
                $this->setMwGlobals( [ 'wgAuth' => null ] );
                $this->stashMwGlobals( [ 'wgHooks' ] );
@@ -200,14 +195,6 @@ class AuthManagerTest extends \MediaWikiTestCase {
                        \RequestContext::getMain()->getConfig(),
                        \TestingAccessWrapper::newFromObject( $singleton )->config
                );
-
-               $this->setMwGlobals( [ 'wgDisableAuthManager' => true ] );
-               try {
-                       AuthManager::singleton();
-                       $this->fail( 'Expected exception not thrown' );
-               } catch ( \BadMethodCallException $ex ) {
-                       $this->assertSame( '$wgDisableAuthManager is set', $ex->getMessage() );
-               }
        }
 
        public function testCanAuthenticateNow() {
index 44f2743..96e50e0 100644 (file)
@@ -7,15 +7,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\AuthPluginPrimaryAuthenticationProvider
  */
 class AuthPluginPrimaryAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        public function testConstruction() {
                $plugin = new AuthManagerAuthPlugin();
                try {
index cac031c..a7df221 100644 (file)
@@ -7,15 +7,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\AuthenticationRequest
  */
 class AuthenticationRequestTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        public function testBasics() {
                $mock = $this->getMockForAbstractClass( AuthenticationRequest::class );
 
index aafcd09..aa0e3c7 100644 (file)
@@ -6,15 +6,6 @@ namespace MediaWiki\Auth;
  * @group AuthManager
  */
 abstract class AuthenticationRequestTestCase extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        abstract protected function getInstance( array $args = [] );
 
        /**
index 58ff8b6..477b161 100644 (file)
@@ -7,15 +7,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\AuthenticationResponse
  */
 class AuthenticationResponseTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        /**
         * @dataProvider provideConstructors
         * @param string $constructor
index f2341bc..e6d3ecf 100644 (file)
@@ -8,15 +8,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\CheckBlocksSecondaryAuthenticationProvider
  */
 class CheckBlocksSecondaryAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        public function testConstructor() {
                $provider = new CheckBlocksSecondaryAuthenticationProvider();
                $providerPriv = \TestingAccessWrapper::newFromObject( $provider );
index 580ef6c..3fc45a4 100644 (file)
@@ -7,15 +7,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\ConfirmLinkSecondaryAuthenticationProvider
  */
 class ConfirmLinkSecondaryAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        /**
         * @dataProvider provideGetAuthenticationRequests
         * @param string $action
index 3548002..d482453 100644 (file)
@@ -8,15 +8,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\LegacyHookPreAuthenticationProvider
  */
 class LegacyHookPreAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        /**
         * Get an instance of the provider
         * @return LegacyHookPreAuthenticationProvider
index 713c27e..088dd00 100644 (file)
@@ -13,15 +13,6 @@ class LocalPasswordPrimaryAuthenticationProviderTest extends \MediaWikiTestCase
        private $config = null;
        private $validity = null;
 
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        /**
         * Get an instance of the provider
         *
index 79c138b..90ed542 100644 (file)
@@ -7,15 +7,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\ResetPasswordSecondaryAuthenticationProvider
  */
 class ResetPasswordSecondaryAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        /**
         * @dataProvider provideGetAuthenticationRequests
         * @param string $action
index 8d0bf96..515a5b3 100644 (file)
@@ -13,15 +13,6 @@ class TemporaryPasswordPrimaryAuthenticationProviderTest extends \MediaWikiTestC
        private $config = null;
        private $validity = null;
 
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        /**
         * Get an instance of the provider
         *
index 8b273b5..aa6f0e8 100644 (file)
@@ -8,15 +8,6 @@ namespace MediaWiki\Auth;
  * @covers MediaWiki\Auth\ThrottlePreAuthenticationProvider
  */
 class ThrottlePreAuthenticationProviderTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        public function testConstructor() {
                $provider = new ThrottlePreAuthenticationProvider();
                $providerPriv = \TestingAccessWrapper::newFromObject( $provider );
index dba748b..5806003 100644 (file)
@@ -14,15 +14,6 @@ use Psr\Log\NullLogger;
  * @covers MediaWiki\Auth\Throttler
  */
 class ThrottlerTest extends \MediaWikiTestCase {
-       protected function setUp() {
-               global $wgDisableAuthManager;
-
-               parent::setUp();
-               if ( $wgDisableAuthManager ) {
-                       $this->markTestSkipped( '$wgDisableAuthManager is set' );
-               }
-       }
-
        public function testConstructor() {
                $cache = new \HashBagOStuff();
                $logger = $this->getMockBuilder( AbstractLogger::class )
index bb7eb79..bc7542a 100644 (file)
@@ -76,9 +76,6 @@ class FakeDatabaseMysqlBase extends DatabaseMysqlBase {
        protected function mysqlFetchField( $res, $n ) {
        }
 
-       protected function mysqlPing() {
-       }
-
        protected function mysqlRealEscapeString( $s ) {
 
        }
index a8beb91..92fb954 100644 (file)
@@ -138,6 +138,20 @@ class BagOStuffTest extends MediaWikiTestCase {
                }
        }
 
+       /**
+        * @covers BagOStuff::changeTTL
+        */
+       public function testChangeTTL() {
+               $key = wfMemcKey( 'test' );
+               $value = 'meow';
+
+               $this->cache->add( $key, $value );
+               $this->assertTrue( $this->cache->changeTTL( $key, 5 ) );
+               $this->assertEquals( $this->cache->get( $key ), $value );
+               $this->cache->delete( $key );
+               $this->assertFalse( $this->cache->changeTTL( $key, 5 ) );
+       }
+
        /**
         * @covers BagOStuff::add
         */
diff --git a/tests/phpunit/includes/resourceloader/ResourceLoaderClientHtmlTest.php b/tests/phpunit/includes/resourceloader/ResourceLoaderClientHtmlTest.php
new file mode 100644 (file)
index 0000000..0965b9f
--- /dev/null
@@ -0,0 +1,278 @@
+<?php
+
+/**
+ * @group ResourceLoader
+ */
+class ResourceLoaderClientHtmlTest extends PHPUnit_Framework_TestCase {
+
+       protected static function makeContext( $extraQuery = [] ) {
+               $conf = new HashConfig( [
+                       'ResourceLoaderSources' => [],
+                       'ResourceModuleSkinStyles' => [],
+                       'ResourceModules' => [],
+                       'EnableJavaScriptTest' => false,
+                       'ResourceLoaderDebug' => false,
+                       'LoadScript' => '/w/load.php',
+               ] );
+               return new ResourceLoaderContext(
+                       new ResourceLoader( $conf ),
+                       new FauxRequest( array_merge( [
+                               'lang' => 'nl',
+                               'skin' => 'fallback',
+                               'user' => 'Example',
+                               'target' => 'phpunit',
+                       ], $extraQuery ) )
+               );
+       }
+
+       protected static function makeModule( array $options = [] ) {
+               return new ResourceLoaderTestModule( $options );
+       }
+
+       protected static function makeSampleModules() {
+               $modules = [
+                       'test' => [],
+                       'test.top' => [ 'position' => 'top' ],
+                       'test.private.top' => [ 'group' => 'private', 'position' => 'top' ],
+                       'test.private.bottom' => [ 'group' => 'private', 'position' => 'bottom' ],
+
+                       'test.styles.pure' => [ 'type' => ResourceLoaderModule::LOAD_STYLES ],
+                       'test.styles.mixed' => [],
+                       'test.styles.noscript' => [ 'group' => 'noscript', 'type' => ResourceLoaderModule::LOAD_STYLES ],
+                       'test.styles.mixed.user' => [ 'group' => 'user' ],
+                       'test.styles.mixed.user.empty' => [ 'group' => 'user', 'isKnownEmpty' => true ],
+                       'test.styles.private' => [ 'group' => 'private', 'styles' => '.private{}' ],
+
+                       'test.scripts' => [],
+                       'test.scripts.top' => [ 'position' => 'top' ],
+                       'test.scripts.mixed.user' => [ 'group' => 'user' ],
+                       'test.scripts.mixed.user.empty' => [ 'group' => 'user', 'isKnownEmpty' => true ],
+                       'test.scripts.raw' => [ 'isRaw' => true ],
+               ];
+               return array_map( function ( $options ) {
+                       return self::makeModule( $options );
+               }, $modules );
+       }
+
+       /**
+        * @covers ResourceLoaderClientHtml::getDocumentAttributes
+        */
+       public function testGetDocumentAttributes() {
+               $client = new ResourceLoaderClientHtml( self::makeContext() );
+               $this->assertInternalType( 'array', $client->getDocumentAttributes() );
+       }
+
+       /**
+        * @covers ResourceLoaderClientHtml::__construct
+        * @covers ResourceLoaderClientHtml::setModules
+        * @covers ResourceLoaderClientHtml::setModuleStyles
+        * @covers ResourceLoaderClientHtml::setModuleScripts
+        * @covers ResourceLoaderClientHtml::getData
+        * @covers ResourceLoaderClientHtml::getContext
+        */
+       public function testGetData() {
+               $context = self::makeContext();
+               $context->getResourceLoader()->register( self::makeSampleModules() );
+
+               $client = new ResourceLoaderClientHtml( $context );
+               $client->setModules( [
+                       'test',
+                       'test.private.bottom',
+                       'test.private.top',
+                       'test.top',
+                       'test.unregistered',
+               ] );
+               $client->setModuleStyles( [
+                       'test.styles.mixed',
+                       'test.styles.mixed.user.empty',
+                       'test.styles.private',
+                       'test.styles.pure',
+                       'test.unregistered.styles',
+               ] );
+               $client->setModuleScripts( [
+                       'test.scripts',
+                       'test.scripts.mixed.user.empty',
+                       'test.scripts.top',
+                       'test.unregistered.scripts',
+               ] );
+
+               $expected = [
+                       'states' => [
+                               'test.private.top' => 'loading',
+                               'test.private.bottom' => 'loading',
+                               'test.styles.pure' => 'ready',
+                               'test.styles.mixed.user.empty' => 'ready',
+                               'test.styles.private' => 'ready',
+                               'test.scripts' => 'loading',
+                               'test.scripts.top' => 'loading',
+                               'test.scripts.mixed.user.empty' => 'ready',
+                       ],
+                       'general' => [
+                               'top' => [ 'test.top' ],
+                               'bottom' => [ 'test' ],
+                       ],
+                       'styles' => [
+                               'test.styles.mixed',
+                               'test.styles.pure',
+                       ],
+                       'scripts' => [
+                               'top' => [ 'test.scripts.top' ],
+                               'bottom' => [ 'test.scripts' ],
+                       ],
+                       'embed' => [
+                               'styles' => [ 'test.styles.private' ],
+                               'general' => [
+                                       'top' => [ 'test.private.top' ],
+                                       'bottom' => [ 'test.private.bottom' ],
+                               ],
+                       ],
+               ];
+
+               $access = TestingAccessWrapper::newFromObject( $client );
+               $this->assertEquals( $expected, $access->getData() );
+       }
+
+       /**
+        * @covers ResourceLoaderClientHtml::setConfig
+        * @covers ResourceLoaderClientHtml::setExemptStates
+        * @covers ResourceLoaderClientHtml::getHeadHtml
+        * @covers ResourceLoaderClientHtml::getLoad
+        * @covers ResourceLoader::makeLoaderStateScript
+        */
+       public function testGetHeadHtml() {
+               $context = self::makeContext();
+               $context->getResourceLoader()->register( self::makeSampleModules() );
+
+               $client = new ResourceLoaderClientHtml( $context );
+               $client->setConfig( [ 'key' => 'value' ] );
+               $client->setModules( [
+                       'test.top',
+                       'test.private.top',
+               ] );
+               $client->setModuleStyles( [
+                       'test.styles.pure',
+                       'test.styles.private',
+               ] );
+               $client->setModuleScripts( [
+                       'test.scripts.top',
+               ] );
+               $client->setExemptStates( [
+                       'test.exempt' => 'ready',
+               ] );
+
+               // @codingStandardsIgnoreStart Generic.Files.LineLength
+               $expected = '<script>document.documentElement.className = document.documentElement.className.replace( /(^|\s)client-nojs(\s|$)/, "$1client-js$2" );</script>' . "\n"
+                       . '<script>(window.RLQ=window.RLQ||[]).push(function(){'
+                       . 'mw.config.set({"key":"value"});'
+                       . 'mw.loader.state({"test.exempt":"ready","test.private.top":"loading","test.styles.pure":"ready","test.styles.private":"ready","test.scripts.top":"loading"});'
+                       . 'mw.loader.implement("test.private.top",function($,jQuery,require,module){},{"css":[]});'
+                       . 'mw.loader.load(["test.top"]);'
+                       . 'mw.loader.load("/w/load.php?debug=false\u0026lang=nl\u0026modules=test.scripts.top\u0026only=scripts\u0026skin=fallback");'
+                       . '});</script>' . "\n"
+                       . '<link rel="stylesheet" href="/w/load.php?debug=false&amp;lang=nl&amp;modules=test.styles.pure&amp;only=styles&amp;skin=fallback"/>' . "\n"
+                       . '<style>.private{}</style>' . "\n"
+                       . '<script async="" src="/w/load.php?debug=false&amp;lang=nl&amp;modules=startup&amp;only=scripts&amp;skin=fallback"></script>';
+               // @codingStandardsIgnoreEnd
+
+               $this->assertEquals( $expected, $client->getHeadHtml() );
+       }
+
+       /**
+        * @covers ResourceLoaderClientHtml::getBodyHtml
+        * @covers ResourceLoaderClientHtml::getLoad
+        */
+       public function testGetBodyHtml() {
+               $context = self::makeContext();
+               $context->getResourceLoader()->register( self::makeSampleModules() );
+
+               $client = new ResourceLoaderClientHtml( $context );
+               $client->setConfig( [ 'key' => 'value' ] );
+               $client->setModules( [
+                       'test',
+                       'test.private.bottom',
+               ] );
+               $client->setModuleScripts( [
+                       'test.scripts',
+               ] );
+
+               // @codingStandardsIgnoreStart Generic.Files.LineLength
+               $expected = '<script>(window.RLQ=window.RLQ||[]).push(function(){'
+                       . 'mw.loader.implement("test.private.bottom",function($,jQuery,require,module){},{"css":[]});'
+                       . 'mw.loader.load("/w/load.php?debug=false\u0026lang=nl\u0026modules=test.scripts\u0026only=scripts\u0026skin=fallback");'
+                       . 'mw.loader.load(["test"]);'
+                       . '});</script>';
+               // @codingStandardsIgnoreEnd
+
+               $this->assertEquals( $expected, $client->getBodyHtml() );
+       }
+
+       public static function provideMakeLoad() {
+               return [
+                       // @codingStandardsIgnoreStart Generic.Files.LineLength
+                       [
+                               'context' => [],
+                               'modules' => [ 'test.unknown' ],
+                               'only' => ResourceLoaderModule::TYPE_STYLES,
+                               'output' => '',
+                       ],
+                       [
+                               'context' => [],
+                               'modules' => [ 'test.styles.private' ],
+                               'only' => ResourceLoaderModule::TYPE_STYLES,
+                               'output' => '<style>.private{}</style>',
+                       ],
+                       [
+                               'context' => [],
+                               'modules' => [ 'test.private.top' ],
+                               'only' => ResourceLoaderModule::TYPE_COMBINED,
+                               'output' => '<script>(window.RLQ=window.RLQ||[]).push(function(){mw.loader.implement("test.private.top",function($,jQuery,require,module){},{"css":[]});});</script>',
+                       ],
+                       [
+                               'context' => [],
+                               // Eg. startup module
+                               'modules' => [ 'test.scripts.raw' ],
+                               'only' => ResourceLoaderModule::TYPE_SCRIPTS,
+                               'output' => '<script async="" src="/w/load.php?debug=false&amp;lang=nl&amp;modules=test.scripts.raw&amp;only=scripts&amp;skin=fallback"></script>',
+                       ],
+                       [
+                               'context' => [],
+                               'modules' => [ 'test.scripts.mixed.user' ],
+                               'only' => ResourceLoaderModule::TYPE_SCRIPTS,
+                               'output' => '<script>(window.RLQ=window.RLQ||[]).push(function(){mw.loader.load("/w/load.php?debug=false\u0026lang=nl\u0026modules=test.scripts.mixed.user\u0026only=scripts\u0026skin=fallback\u0026user=Example\u0026version=0a56zyi");});</script>',
+                       ],
+                       [
+                               'context' => [ 'debug' => true ],
+                               'modules' => [ 'test.styles.pure', 'test.styles.mixed' ],
+                               'only' => ResourceLoaderModule::TYPE_STYLES,
+                               'output' => '<link rel="stylesheet" href="/w/load.php?debug=true&amp;lang=nl&amp;modules=test.styles.pure&amp;only=styles&amp;skin=fallback"/>' . "\n"
+                                       . '<link rel="stylesheet" href="/w/load.php?debug=true&amp;lang=nl&amp;modules=test.styles.mixed&amp;only=styles&amp;skin=fallback"/>',
+                       ],
+                       [
+                               'context' => [],
+                               'modules' => [ 'test.styles.noscript' ],
+                               'only' => ResourceLoaderModule::TYPE_STYLES,
+                               'output' => '<noscript><link rel="stylesheet" href="/w/load.php?debug=false&amp;lang=nl&amp;modules=test.styles.noscript&amp;only=styles&amp;skin=fallback"/></noscript>',
+                       ],
+                       // @codingStandardsIgnoreEnd
+               ];
+       }
+
+       /**
+        * @dataProvider provideMakeLoad
+        * @covers ResourceLoaderClientHtml::makeLoad
+        * @covers ResourceLoaderClientHtml::makeContext
+        * @covers ResourceLoader::makeModuleResponse
+        * @covers ResourceLoaderModule::getModuleContent
+        * @covers ResourceLoader::getCombinedVersion
+        * @covers ResourceLoader::createLoaderURL
+        * @covers ResourceLoader::createLoaderQuery
+        * @covers ResourceLoader::makeLoaderQuery
+        * @covers ResourceLoader::makeInlineScript
+        */
+       public function testMakeLoad( array $extraQuery, array $modules, $type, $expected ) {
+               $context = self::makeContext( $extraQuery );
+               $context->getResourceLoader()->register( self::makeSampleModules() );
+               $actual = ResourceLoaderClientHtml::makeLoad( $context, $modules, $type );
+               $this->assertEquals( $expected, (string)$actual );
+       }
+}
index e725fee..1ebb07c 100644 (file)
@@ -867,303 +867,6 @@ class SessionManagerTest extends MediaWikiTestCase {
                $this->assertTrue( SessionManager::validateSessionId( $id ), "Generated ID: $id" );
        }
 
-       public function testAutoCreateUser() {
-               global $wgGroupPermissions, $wgDisableAuthManager;
-
-               if ( !$wgDisableAuthManager ) {
-                       $this->markTestSkipped( 'AuthManager is not disabled' );
-               }
-
-               \ObjectCache::$instances[__METHOD__] = new TestBagOStuff();
-               $this->setMwGlobals( [ 'wgMainCacheType' => __METHOD__ ] );
-               $this->setMwGlobals( [
-                       'wgAuth' => new AuthPlugin,
-               ] );
-
-               $this->stashMwGlobals( [ 'wgGroupPermissions' ] );
-               $wgGroupPermissions['*']['createaccount'] = true;
-               $wgGroupPermissions['*']['autocreateaccount'] = false;
-
-               // Replace the global singleton with one configured for testing
-               $manager = $this->getManager();
-               $reset = TestUtils::setSessionManagerSingleton( $manager );
-
-               $logger = new \TestLogger( true, function ( $m ) {
-                       if ( substr( $m, 0, 15 ) === 'SessionBackend ' ) {
-                               // Don't care.
-                               return null;
-                       }
-                       $m = str_replace( 'MediaWiki\Session\SessionManager::autoCreateUser: ', '', $m );
-                       return $m;
-               } );
-               $manager->setLogger( $logger );
-
-               $session = SessionManager::getGlobalSession();
-
-               // Can't create an already-existing user
-               $user = User::newFromName( 'UTSysop' );
-               $id = $user->getId();
-               $this->assertFalse( $manager->autoCreateUser( $user ) );
-               $this->assertSame( $id, $user->getId() );
-               $this->assertSame( 'UTSysop', $user->getName() );
-               $this->assertSame( [], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Sanity check that creation works at all
-               $user = User::newFromName( 'UTSessionAutoCreate1' );
-               $this->assertSame( 0, $user->getId(), 'sanity check' );
-               $this->assertTrue( $manager->autoCreateUser( $user ) );
-               $this->assertNotEquals( 0, $user->getId() );
-               $this->assertSame( 'UTSessionAutoCreate1', $user->getName() );
-               $this->assertEquals(
-                       $user->getId(), User::idFromName( 'UTSessionAutoCreate1', User::READ_LATEST )
-               );
-               $this->assertSame( [
-                       [ LogLevel::INFO, 'creating new user ({username}) - from: {url}' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Check lack of permissions
-               $wgGroupPermissions['*']['createaccount'] = false;
-               $wgGroupPermissions['*']['autocreateaccount'] = false;
-               $user = User::newFromName( 'UTDoesNotExist' );
-               $this->assertFalse( $manager->autoCreateUser( $user ) );
-               $this->assertSame( 0, $user->getId() );
-               $this->assertNotSame( 'UTDoesNotExist', $user->getName() );
-               $this->assertEquals( 0, User::idFromName( 'UTDoesNotExist', User::READ_LATEST ) );
-               $session->clear();
-               $this->assertSame( [
-                       [
-                               LogLevel::DEBUG,
-                               'user is blocked from this wiki, blacklisting',
-                       ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Check other permission
-               $wgGroupPermissions['*']['createaccount'] = false;
-               $wgGroupPermissions['*']['autocreateaccount'] = true;
-               $user = User::newFromName( 'UTSessionAutoCreate2' );
-               $this->assertSame( 0, $user->getId(), 'sanity check' );
-               $this->assertTrue( $manager->autoCreateUser( $user ) );
-               $this->assertNotEquals( 0, $user->getId() );
-               $this->assertSame( 'UTSessionAutoCreate2', $user->getName() );
-               $this->assertEquals(
-                       $user->getId(), User::idFromName( 'UTSessionAutoCreate2', User::READ_LATEST )
-               );
-               $this->assertSame( [
-                       [ LogLevel::INFO, 'creating new user ({username}) - from: {url}' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Test account-creation block
-               $anon = new User;
-               $block = new \Block( [
-                       'address' => $anon->getName(),
-                       'user' => $id,
-                       'reason' => __METHOD__,
-                       'expiry' => time() + 100500,
-                       'createAccount' => true,
-               ] );
-               $block->insert();
-               $this->assertInstanceOf( 'Block', $anon->isBlockedFromCreateAccount(), 'sanity check' );
-               $reset2 = new \ScopedCallback( [ $block, 'delete' ] );
-               $user = User::newFromName( 'UTDoesNotExist' );
-               $this->assertFalse( $manager->autoCreateUser( $user ) );
-               $this->assertSame( 0, $user->getId() );
-               $this->assertNotSame( 'UTDoesNotExist', $user->getName() );
-               $this->assertEquals( 0, User::idFromName( 'UTDoesNotExist', User::READ_LATEST ) );
-               \ScopedCallback::consume( $reset2 );
-               $session->clear();
-               $this->assertSame( [
-                       [ LogLevel::DEBUG, 'user is blocked from this wiki, blacklisting' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Sanity check that creation still works
-               $user = User::newFromName( 'UTSessionAutoCreate3' );
-               $this->assertSame( 0, $user->getId(), 'sanity check' );
-               $this->assertTrue( $manager->autoCreateUser( $user ) );
-               $this->assertNotEquals( 0, $user->getId() );
-               $this->assertSame( 'UTSessionAutoCreate3', $user->getName() );
-               $this->assertEquals(
-                       $user->getId(), User::idFromName( 'UTSessionAutoCreate3', User::READ_LATEST )
-               );
-               $this->assertSame( [
-                       [ LogLevel::INFO, 'creating new user ({username}) - from: {url}' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Test prevention by AuthPlugin
-               global $wgAuth;
-               $oldWgAuth = $wgAuth;
-               $mockWgAuth = $this->getMock( 'AuthPlugin', [ 'autoCreate' ] );
-               $mockWgAuth->expects( $this->once() )->method( 'autoCreate' )
-                       ->will( $this->returnValue( false ) );
-               $this->setMwGlobals( [
-                       'wgAuth' => $mockWgAuth,
-               ] );
-               $user = User::newFromName( 'UTDoesNotExist' );
-               $this->assertFalse( $manager->autoCreateUser( $user ) );
-               $this->assertSame( 0, $user->getId() );
-               $this->assertNotSame( 'UTDoesNotExist', $user->getName() );
-               $this->assertEquals( 0, User::idFromName( 'UTDoesNotExist', User::READ_LATEST ) );
-               $this->setMwGlobals( [
-                       'wgAuth' => $oldWgAuth,
-               ] );
-               $session->clear();
-               $this->assertSame( [
-                       [ LogLevel::DEBUG, 'denied by AuthPlugin' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Test prevention by wfReadOnly()
-               $this->setMwGlobals( [
-                       'wgReadOnly' => 'Because',
-               ] );
-               $user = User::newFromName( 'UTDoesNotExist' );
-               $this->assertFalse( $manager->autoCreateUser( $user ) );
-               $this->assertSame( 0, $user->getId() );
-               $this->assertNotSame( 'UTDoesNotExist', $user->getName() );
-               $this->assertEquals( 0, User::idFromName( 'UTDoesNotExist', User::READ_LATEST ) );
-               $this->setMwGlobals( [
-                       'wgReadOnly' => false,
-               ] );
-               $session->clear();
-               $this->assertSame( [
-                       [ LogLevel::DEBUG, 'denied by wfReadOnly()' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Test prevention by a previous session
-               $session->set( 'MWSession::AutoCreateBlacklist', 'test' );
-               $user = User::newFromName( 'UTDoesNotExist' );
-               $this->assertFalse( $manager->autoCreateUser( $user ) );
-               $this->assertSame( 0, $user->getId() );
-               $this->assertNotSame( 'UTDoesNotExist', $user->getName() );
-               $this->assertEquals( 0, User::idFromName( 'UTDoesNotExist', User::READ_LATEST ) );
-               $session->clear();
-               $this->assertSame( [
-                       [ LogLevel::DEBUG, 'blacklisted in session (test)' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Test uncreatable name
-               $user = User::newFromName( 'UTDoesNotExist@' );
-               $this->assertFalse( $manager->autoCreateUser( $user ) );
-               $this->assertSame( 0, $user->getId() );
-               $this->assertNotSame( 'UTDoesNotExist@', $user->getName() );
-               $this->assertEquals( 0, User::idFromName( 'UTDoesNotExist', User::READ_LATEST ) );
-               $session->clear();
-               $this->assertSame( [
-                       [ LogLevel::DEBUG, 'Invalid username, blacklisting' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Test AbortAutoAccount hook
-               $mock = $this->getMock( __CLASS__, [ 'onAbortAutoAccount' ] );
-               $mock->expects( $this->once() )->method( 'onAbortAutoAccount' )
-                       ->will( $this->returnCallback( function ( User $user, &$msg ) {
-                               $msg = 'No way!';
-                               return false;
-                       } ) );
-               $this->mergeMwGlobalArrayValue( 'wgHooks', [ 'AbortAutoAccount' => [ $mock ] ] );
-               $user = User::newFromName( 'UTDoesNotExist' );
-               $this->assertFalse( $manager->autoCreateUser( $user ) );
-               $this->assertSame( 0, $user->getId() );
-               $this->assertNotSame( 'UTDoesNotExist', $user->getName() );
-               $this->assertEquals( 0, User::idFromName( 'UTDoesNotExist', User::READ_LATEST ) );
-               $this->mergeMwGlobalArrayValue( 'wgHooks', [ 'AbortAutoAccount' => [] ] );
-               $session->clear();
-               $this->assertSame( [
-                       [ LogLevel::DEBUG, 'denied by hook: No way!' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Test AbortAutoAccount hook screwing up the name
-               $mock = $this->getMock( 'stdClass', [ 'onAbortAutoAccount' ] );
-               $mock->expects( $this->once() )->method( 'onAbortAutoAccount' )
-                       ->will( $this->returnCallback( function ( User $user ) {
-                               $user->setName( 'UTDoesNotExistEither' );
-                       } ) );
-               $this->mergeMwGlobalArrayValue( 'wgHooks', [ 'AbortAutoAccount' => [ $mock ] ] );
-               try {
-                       $user = User::newFromName( 'UTDoesNotExist' );
-                       $manager->autoCreateUser( $user );
-                       $this->fail( 'Expected exception not thrown' );
-               } catch ( \UnexpectedValueException $ex ) {
-                       $this->assertSame(
-                               'AbortAutoAccount hook tried to change the user name',
-                               $ex->getMessage()
-                       );
-               }
-               $this->assertSame( 0, $user->getId() );
-               $this->assertNotSame( 'UTDoesNotExist', $user->getName() );
-               $this->assertNotSame( 'UTDoesNotExistEither', $user->getName() );
-               $this->assertEquals( 0, User::idFromName( 'UTDoesNotExist', User::READ_LATEST ) );
-               $this->assertEquals( 0, User::idFromName( 'UTDoesNotExistEither', User::READ_LATEST ) );
-               $this->mergeMwGlobalArrayValue( 'wgHooks', [ 'AbortAutoAccount' => [] ] );
-               $session->clear();
-               $this->assertSame( [], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Test for "exception backoff"
-               $user = User::newFromName( 'UTDoesNotExist' );
-               $cache = \ObjectCache::getLocalClusterInstance();
-               $backoffKey = wfMemcKey( 'MWSession', 'autocreate-failed', md5( $user->getName() ) );
-               $cache->set( $backoffKey, 1, 60 * 10 );
-               $this->assertFalse( $manager->autoCreateUser( $user ) );
-               $this->assertSame( 0, $user->getId() );
-               $this->assertNotSame( 'UTDoesNotExist', $user->getName() );
-               $this->assertEquals( 0, User::idFromName( 'UTDoesNotExist', User::READ_LATEST ) );
-               $cache->delete( $backoffKey );
-               $session->clear();
-               $this->assertSame( [
-                       [ LogLevel::DEBUG, 'denied by prior creation attempt failures' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-
-               // Sanity check that creation still works, and test completion hook
-               $cb = $this->callback( function ( User $user ) {
-                       $this->assertNotEquals( 0, $user->getId() );
-                       $this->assertSame( 'UTSessionAutoCreate4', $user->getName() );
-                       $this->assertEquals(
-                               $user->getId(), User::idFromName( 'UTSessionAutoCreate4', User::READ_LATEST )
-                       );
-                       return true;
-               } );
-               $mock = $this->getMock( 'stdClass',
-                       [ 'onAuthPluginAutoCreate', 'onLocalUserCreated' ] );
-               $mock->expects( $this->once() )->method( 'onAuthPluginAutoCreate' )
-                       ->with( $cb );
-               $mock->expects( $this->once() )->method( 'onLocalUserCreated' )
-                       ->with( $cb, $this->identicalTo( true ) );
-               $this->mergeMwGlobalArrayValue( 'wgHooks', [
-                       'AuthPluginAutoCreate' => [ $mock ],
-                       'LocalUserCreated' => [ $mock ],
-               ] );
-               $user = User::newFromName( 'UTSessionAutoCreate4' );
-               $this->assertSame( 0, $user->getId(), 'sanity check' );
-               $this->assertTrue( $manager->autoCreateUser( $user ) );
-               $this->assertNotEquals( 0, $user->getId() );
-               $this->assertSame( 'UTSessionAutoCreate4', $user->getName() );
-               $this->assertEquals(
-                       $user->getId(),
-                       User::idFromName( 'UTSessionAutoCreate4', User::READ_LATEST )
-               );
-               $this->mergeMwGlobalArrayValue( 'wgHooks', [
-                       'AuthPluginAutoCreate' => [],
-                       'LocalUserCreated' => [],
-               ] );
-               $this->assertSame( [
-                       [ LogLevel::INFO, 'creating new user ({username}) - from: {url}' ],
-               ], $logger->getBuffer() );
-               $logger->clearBuffer();
-       }
-
-       public function onAbortAutoAccount( User $user, &$msg ) {
-       }
-
        public function testPreventSessionsForUser() {
                $manager = $this->getManager();
 
index 9e3a620..ff544cd 100644 (file)
@@ -35,7 +35,7 @@ class SkinTemplateTest extends MediaWikiTestCase {
                                        'text' => 'text'
                                ],
                                [],
-                               'Test makteListItem with normal values'
+                               'Test makeListItem with normal values'
                        ]
                ];
        }
index baaa66b..a70946a 100755 (executable)
@@ -77,7 +77,7 @@ class PHPUnitMaintClass extends Maintenance {
                global $wgDevelopmentWarnings;
                global $wgSessionProviders, $wgSessionPbkdf2Iterations;
                global $wgJobTypeConf;
-               global $wgAuthManagerConfig, $wgAuth, $wgDisableAuthManager;
+               global $wgAuthManagerConfig, $wgAuth;
 
                // Inject test autoloader
                require_once __DIR__ . '/../TestsAutoLoader.php';
@@ -147,7 +147,7 @@ class PHPUnitMaintClass extends Maintenance {
                        ],
                        'secondaryauth' => [],
                ];
-               $wgAuth = $wgDisableAuthManager ? new AuthPlugin : new MediaWiki\Auth\AuthManagerAuthPlugin();
+               $wgAuth = new MediaWiki\Auth\AuthManagerAuthPlugin();
 
                // Bug 44192 Do not attempt to send a real e-mail
                Hooks::clear( 'AlternateUserMailer' );
index b09bb28..ca26aaf 100644 (file)
                        [ 'Strasse' ]
                ],
 
+               // Data set "digraph"
+               digraphWords = [
+                       [ 'London' ],
+                       [ 'Ljubljana' ],
+                       [ 'Luxembourg' ],
+                       [ 'Njivice' ],
+                       [ 'Norwich' ],
+                       [ 'New York' ]
+               ],
+               digraphWordsSorted = [
+                       [ 'London' ],
+                       [ 'Luxembourg' ],
+                       [ 'Ljubljana' ],
+                       [ 'New York' ],
+                       [ 'Norwich' ],
+                       [ 'Njivice' ]
+               ],
+
                complexMDYDates = [
                        [ 'January, 19 2010' ],
                        [ 'April 21 1991' ],
                }
        );
 
+       tableTest(
+               'Digraphs with custom collation',
+               [ 'City' ],
+               digraphWords,
+               digraphWordsSorted,
+               function ( $table ) {
+                       mw.config.set( 'tableSorterCollation', {
+                               lj: 'lzzzz',
+                               nj: 'nzzzz'
+                       } );
+
+                       $table.tablesorter();
+                       $table.find( '.headerSort:eq(0)' ).click();
+               }
+       );
+
        QUnit.test( 'Rowspan not exploded on init', 1, function ( assert ) {
                var $table = tableCreate( header, planets );
 
index dd43c55..baec37c 100644 (file)
                );
        }
 
-       QUnit.asyncTest( 'mw.loader', 2, function ( assert ) {
+       QUnit.test( 'mw.loader', 2, function ( assert ) {
                var isAwesomeDone;
 
                mw.loader.testCallback = function () {
-                       QUnit.start();
                        assert.strictEqual( isAwesomeDone, undefined, 'Implementing module is.awesome: isAwesomeDone should still be undefined' );
                        isAwesomeDone = true;
                };
 
                mw.loader.implement( 'test.callback', [ QUnit.fixurl( mw.config.get( 'wgScriptPath' ) + '/tests/qunit/data/callMwLoaderTestCallback.js' ) ] );
 
-               mw.loader.using( 'test.callback', function () {
-
-                       // /sample/awesome.js declares the "mw.loader.testCallback" function
-                       // which contains a call to start() and ok()
+               return mw.loader.using( 'test.callback', function () {
                        assert.strictEqual( isAwesomeDone, true, 'test.callback module should\'ve caused isAwesomeDone to be true' );
                        delete mw.loader.testCallback;
 
                }, function () {
-                       QUnit.start();
                        assert.ok( false, 'Error callback fired while loader.using "test.callback" module' );
                } );
        } );
 
-       QUnit.asyncTest( 'mw.loader with Object method as module name', 2, function ( assert ) {
+       QUnit.test( 'mw.loader with Object method as module name', 2, function ( assert ) {
                var isAwesomeDone;
 
                mw.loader.testCallback = function () {
-                       QUnit.start();
                        assert.strictEqual( isAwesomeDone, undefined, 'Implementing module hasOwnProperty: isAwesomeDone should still be undefined' );
                        isAwesomeDone = true;
                };
 
                mw.loader.implement( 'hasOwnProperty', [ QUnit.fixurl( mw.config.get( 'wgScriptPath' ) + '/tests/qunit/data/callMwLoaderTestCallback.js' ) ], {}, {} );
 
-               mw.loader.using( 'hasOwnProperty', function () {
-
-                       // /sample/awesome.js declares the "mw.loader.testCallback" function
-                       // which contains a call to start() and ok()
+               return mw.loader.using( 'hasOwnProperty', function () {
                        assert.strictEqual( isAwesomeDone, true, 'hasOwnProperty module should\'ve caused isAwesomeDone to be true' );
                        delete mw.loader.testCallback;
 
                }, function () {
-                       QUnit.start();
                        assert.ok( false, 'Error callback fired while loader.using "hasOwnProperty" module' );
                } );
        } );
 
-       QUnit.asyncTest( 'mw.loader.using( .. ) Promise', 2, function ( assert ) {
+       QUnit.test( 'mw.loader.using( .. ) Promise', 2, function ( assert ) {
                var isAwesomeDone;
 
                mw.loader.testCallback = function () {
-                       QUnit.start();
                        assert.strictEqual( isAwesomeDone, undefined, 'Implementing module is.awesome: isAwesomeDone should still be undefined' );
                        isAwesomeDone = true;
                };
 
                mw.loader.implement( 'test.promise', [ QUnit.fixurl( mw.config.get( 'wgScriptPath' ) + '/tests/qunit/data/callMwLoaderTestCallback.js' ) ] );
 
-               mw.loader.using( 'test.promise' )
+               return mw.loader.using( 'test.promise' )
                .done( function () {
-
-                       // /sample/awesome.js declares the "mw.loader.testCallback" function
-                       // which contains a call to start() and ok()
                        assert.strictEqual( isAwesomeDone, true, 'test.promise module should\'ve caused isAwesomeDone to be true' );
                        delete mw.loader.testCallback;
 
                } )
                .fail( function () {
-                       QUnit.start();
                        assert.ok( false, 'Error callback fired while loader.using "test.promise" module' );
                } );
        } );
 
-       QUnit.asyncTest( 'mw.loader.implement( styles={ "css": [text, ..] } )', 2, function ( assert ) {
+       QUnit.test( 'mw.loader.implement( styles={ "css": [text, ..] } )', 2, function ( assert ) {
                var $element = $( '<div class="mw-test-implement-a"></div>' ).appendTo( '#qunit-fixture' );
 
                assert.notEqual(
                                        'right',
                                        'style is applied'
                                );
-                               QUnit.start();
                        },
                        {
                                all: '.mw-test-implement-a { float: right; }'
                        }
                );
 
-               mw.loader.load( [
-                       'test.implement.a'
-               ] );
+               return mw.loader.using( 'test.implement.a' );
        } );
 
-       QUnit.asyncTest( 'mw.loader.implement( styles={ "url": { <media>: [url, ..] } } )', 7, function ( assert ) {
+       QUnit.test( 'mw.loader.implement( styles={ "url": { <media>: [url, ..] } } )', 7, function ( assert ) {
                var $element1 = $( '<div class="mw-test-implement-b1"></div>' ).appendTo( '#qunit-fixture' ),
                        $element2 = $( '<div class="mw-test-implement-b2"></div>' ).appendTo( '#qunit-fixture' ),
-                       $element3 = $( '<div class="mw-test-implement-b3"></div>' ).appendTo( '#qunit-fixture' );
+                       $element3 = $( '<div class="mw-test-implement-b3"></div>' ).appendTo( '#qunit-fixture' ),
+                       done = assert.async();
 
                assert.notEqual(
                        $element1.css( 'text-align' ),
                mw.loader.implement(
                        'test.implement.b',
                        function () {
-                               // Note: QUnit.start() must only be called when the entire test is
+                               // Note: done() must only be called when the entire test is
                                // complete. So, make sure that we don't start until *both*
                                // assertStyleAsync calls have completed.
                                var pending = 2;
 
                                        pending--;
                                        if ( pending === 0 ) {
-                                               QUnit.start();
+                                               done();
                                        }
                                } );
                                assertStyleAsync( assert, $element3, 'float', 'right', function () {
 
                                        pending--;
                                        if ( pending === 0 ) {
-                                               QUnit.start();
+                                               done();
                                        }
                                } );
                        },
                        }
                );
 
-               mw.loader.load( [
-                       'test.implement.b'
-               ] );
+               mw.loader.load( 'test.implement.b' );
        } );
 
        // Backwards compatibility
-       QUnit.asyncTest( 'mw.loader.implement( styles={ <media>: text } ) (back-compat)', 2, function ( assert ) {
+       QUnit.test( 'mw.loader.implement( styles={ <media>: text } ) (back-compat)', 2, function ( assert ) {
                var $element = $( '<div class="mw-test-implement-c"></div>' ).appendTo( '#qunit-fixture' );
 
                assert.notEqual(
                                        'right',
                                        'style is applied'
                                );
-                               QUnit.start();
                        },
                        {
                                all: '.mw-test-implement-c { float: right; }'
                        }
                );
 
-               mw.loader.load( [
-                       'test.implement.c'
-               ] );
+               return mw.loader.using( 'test.implement.c' );
        } );
 
        // Backwards compatibility
-       QUnit.asyncTest( 'mw.loader.implement( styles={ <media>: [url, ..] } ) (back-compat)', 4, function ( assert ) {
+       QUnit.test( 'mw.loader.implement( styles={ <media>: [url, ..] } ) (back-compat)', 4, function ( assert ) {
                var $element = $( '<div class="mw-test-implement-d"></div>' ).appendTo( '#qunit-fixture' ),
-                       $element2 = $( '<div class="mw-test-implement-d2"></div>' ).appendTo( '#qunit-fixture' );
+                       $element2 = $( '<div class="mw-test-implement-d2"></div>' ).appendTo( '#qunit-fixture' ),
+                       done = assert.async();
 
                assert.notEqual(
                        $element.css( 'float' ),
                        'test.implement.d',
                        function () {
                                assertStyleAsync( assert, $element, 'float', 'right', function () {
-
                                        assert.notEqual( $element2.css( 'text-align' ), 'center', 'print style is not applied (bug 40500)' );
-
-                                       QUnit.start();
+                                       done();
                                } );
                        },
                        {
                        }
                );
 
-               mw.loader.load( [
-                       'test.implement.d'
-               ] );
+               mw.loader.load( 'test.implement.d' );
        } );
 
        // @import (bug 31676)
-       QUnit.asyncTest( 'mw.loader.implement( styles has @import )', 7, function ( assert ) {
-               var isJsExecuted, $element;
+       QUnit.test( 'mw.loader.implement( styles has @import )', 7, function ( assert ) {
+               var isJsExecuted, $element,
+                       done = assert.async();
 
                mw.loader.implement(
                        'test.implement.import',
                                                'CSS styles after the @import rule are working'
                                        );
 
-                                       QUnit.start();
+                                       done();
                                } );
                        },
                        {
                } );
        } );
 
-       QUnit.asyncTest( 'mw.loader.implement( dependency with styles )', 4, function ( assert ) {
+       QUnit.test( 'mw.loader.implement( dependency with styles )', 4, function ( assert ) {
                var $element = $( '<div class="mw-test-implement-e"></div>' ).appendTo( '#qunit-fixture' ),
                        $element2 = $( '<div class="mw-test-implement-e2"></div>' ).appendTo( '#qunit-fixture' );
 
                                        'right',
                                        'Depending module\'s style is applied'
                                );
-                               QUnit.start();
                        },
                        {
                                all: '.mw-test-implement-e { float: right; }'
                        }
                );
 
-               mw.loader.load( [
-                       'test.implement.e'
-               ] );
+               return mw.loader.using( 'test.implement.e' );
        } );
 
        QUnit.test( 'mw.loader.implement( only scripts )', 1, function ( assert ) {
                assert.strictEqual( mw.loader.getState( 'test.onlyscripts' ), 'ready' );
        } );
 
-       QUnit.asyncTest( 'mw.loader.implement( only messages )', 2, function ( assert ) {
+       QUnit.test( 'mw.loader.implement( only messages )', 2, function ( assert ) {
                assert.assertFalse( mw.messages.exists( 'bug_29107' ), 'Verify that the test message doesn\'t exist yet' );
 
                // jscs: disable requireCamelCaseOrUpperCaseIdentifiers
                mw.loader.implement( 'test.implement.msgs', [], {}, { bug_29107: 'loaded' } );
                // jscs: enable requireCamelCaseOrUpperCaseIdentifiers
-               mw.loader.using( 'test.implement.msgs', function () {
-                       QUnit.start();
+
+               return mw.loader.using( 'test.implement.msgs', function () {
                        assert.ok( mw.messages.exists( 'bug_29107' ), 'Bug 29107: messages-only module should implement ok' );
                }, function () {
-                       QUnit.start();
                        assert.ok( false, 'Error callback fired while implementing "test.implement.msgs" module' );
                } );
        } );
                );
        } );
 
-       QUnit.asyncTest( 'mw.loader dependency handling', 5, function ( assert ) {
+       QUnit.test( 'mw.loader dependency handling', 5, function ( assert ) {
+               var done = assert.async();
                mw.loader.register( [
                        // [module, version, dependencies, group, source]
                        [ 'testMissing', '1', [], null, 'testloader' ],
 
                                verifyModuleStates();
 
-                               QUnit.start();
+                               done();
                        },
                        function ( e, badmodules ) {
                                assert.ok( true, 'Error handler should be invoked.' );
 
                                verifyModuleStates();
 
-                               QUnit.start();
+                               done();
                        }
                );
        } );
 
-       QUnit.asyncTest( 'mw.loader skin-function handling', 5, function ( assert ) {
+       QUnit.test( 'mw.loader skin-function handling', 5, function ( assert ) {
                mw.loader.register( [
                        // [module, version, dependencies, group, source, skip]
                        [ 'testSkipped', '1', [], null, 'testloader', 'return true;' ],
                        assert.equal( mw.loader.getState( 'testUsesSkippable' ), 'ready', 'Module is ready when skippable dependencies are ready' );
                }
 
-               mw.loader.using( [ 'testUsesSkippable' ],
+               return mw.loader.using( [ 'testUsesSkippable' ],
                        function () {
                                assert.ok( true, 'Success handler should be invoked.' );
                                assert.ok( true ); // Dummy to match error handler and reach QUnit expect()
 
                                verifyModuleStates();
-
-                               QUnit.start();
                        },
                        function ( e, badmodules ) {
                                assert.ok( false, 'Error handler should not be invoked.' );
                                assert.deepEqual( badmodules, [], 'Bad modules as expected.' );
 
                                verifyModuleStates();
-
-                               QUnit.start();
                        }
                );
        } );
                mw.loader.load( target );
        } );
 
-       QUnit.asyncTest( 'mw.loader() executing race (T112232)', 2, function ( assert ) {
+       QUnit.test( 'mw.loader() executing race (T112232)', 2, function ( assert ) {
                var done = false;
 
                // The red herring schedules its CSS buffer first. In T112232, a bug in the
                );
 
                mw.loader.load( [ 'testRaceRedHerring', 'testRaceLoadMe' ] );
-               mw.loader.using( 'testRaceLoadMe', function () {
+               return mw.loader.using( 'testRaceLoadMe', function () {
                        assert.strictEqual( done, true, 'script ran' );
                        assert.strictEqual( mw.loader.getState( 'testRaceLoadMe' ), 'ready', 'state' );
-               } ).always( QUnit.start );
+               } );
        } );
 
        QUnit.test( 'mw.hook', 13, function ( assert ) {
                );
        } );
 
-       QUnit.test( 'mw.loader.require', 6, function ( assert ) {
-               var module1, module2, module3, module4;
-
+       QUnit.test( 'mw.loader require()', 6, function ( assert ) {
                mw.loader.register( [
-                       [ 'test.module.require1', '0' ],
-                       [ 'test.module.require2', '0' ],
-                       [ 'test.module.require3', '0' ],
-                       [ 'test.module.require4', '0', [ 'test.module.require3' ] ]
+                       [ 'test.require1', '0' ],
+                       [ 'test.require2', '0' ],
+                       [ 'test.require3', '0' ],
+                       [ 'test.require4', '0', [ 'test.require3' ] ]
                ] );
-               mw.loader.implement( 'test.module.require1', function () {} );
-               mw.loader.implement( 'test.module.require2', function ( $, jQuery, require, module ) {
+               mw.loader.implement( 'test.require1', function () {} );
+               mw.loader.implement( 'test.require2', function ( $, jQuery, require, module ) {
                        module.exports = 1;
                } );
-               mw.loader.implement( 'test.module.require3', function ( $, jQuery, require, module ) {
+               mw.loader.implement( 'test.require3', function ( $, jQuery, require, module ) {
                        module.exports = function () {
                                return 'hello world';
                        };
                } );
-               mw.loader.implement( 'test.module.require4', function ( $, jQuery, require, module ) {
-                       var other = require( 'test.module.require3' );
+               mw.loader.implement( 'test.require4', function ( $, jQuery, require, module ) {
+                       var other = require( 'test.require3' );
                        module.exports = {
                                pizza: function () {
                                        return other();
                                }
                        };
                } );
-               module1 = mw.loader.require( 'test.module.require1' );
-               module2 = mw.loader.require( 'test.module.require2' );
-               module3 = mw.loader.require( 'test.module.require3' );
-               module4 = mw.loader.require( 'test.module.require4' );
-
-               assert.strictEqual( typeof module1, 'object', 'export of module with no export' );
-               assert.strictEqual( module2, 1, 'export a number' );
-               assert.strictEqual( module3(), 'hello world', 'export a function' );
-               assert.strictEqual( typeof module4.pizza, 'function', 'export an object' );
-               assert.strictEqual( module4.pizza(), 'hello world', 'module can require other modules' );
-
-               assert.throws( function () {
-                       mw.loader.require( '_badmodule' );
-               }, /is not loaded/, 'Requesting non-existent modules throws error.' );
+               return mw.loader.using( [ 'test.require1', 'test.require2', 'test.require3', 'test.require4' ] )
+               .then( function ( require ) {
+                       var module1, module2, module3, module4;
+
+                       module1 = require( 'test.require1' );
+                       module2 = require( 'test.require2' );
+                       module3 = require( 'test.require3' );
+                       module4 = require( 'test.require4' );
+
+                       assert.strictEqual( typeof module1, 'object', 'export of module with no export' );
+                       assert.strictEqual( module2, 1, 'export a number' );
+                       assert.strictEqual( module3(), 'hello world', 'export a function' );
+                       assert.strictEqual( typeof module4.pizza, 'function', 'export an object' );
+                       assert.strictEqual( module4.pizza(), 'hello world', 'module can require other modules' );
+
+                       assert.throws( function () {
+                               require( '_badmodule' );
+                       }, /is not loaded/, 'Requesting non-existent modules throws error.' );
+               } );
        } );
 
-       QUnit.asyncTest( 'mw.loader require in debug mode', 1, function ( assert ) {
+       QUnit.test( 'mw.loader require() in debug mode', 1, function ( assert ) {
                var path = mw.config.get( 'wgScriptPath' );
                mw.loader.register( [
                        [ 'test.require.define', '0' ],
                mw.loader.implement( 'test.require.callback', [ QUnit.fixurl( path + '/tests/qunit/data/requireCallMwLoaderTestCallback.js' ) ] );
                mw.loader.implement( 'test.require.define', [ QUnit.fixurl( path + '/tests/qunit/data/defineCallMwLoaderTestCallback.js' ) ] );
 
-               mw.loader.using( 'test.require.callback', function () {
-                       QUnit.start();
-                       var exported = mw.loader.require( 'test.require.callback' );
+               return mw.loader.using( 'test.require.callback' ).then( function ( require ) {
+                       var exported = require( 'test.require.callback' );
                        assert.strictEqual( exported, 'Require worked.Define worked.',
                                'module.exports worked in debug mode' );
                }, function () {
-                       QUnit.start();
                        assert.ok( false, 'Error callback fired while loader.using "test.require.callback" module' );
                } );
        } );