MediaWiki:Gadget-EditsReview.js
Uwaga: aby zobaczyć zmiany po opublikowaniu, może zajść potrzeba wyczyszczenia pamięci podręcznej przeglądarki.
- Firefox / Safari: Przytrzymaj Shift podczas klikania Odśwież bieżącą stronę, lub naciśnij klawisze Ctrl+F5, lub Ctrl+R (⌘-R na komputerze Mac)
- Google Chrome: Naciśnij Ctrl-Shift-R (⌘-Shift-R na komputerze Mac)
- Internet Explorer / Edge: Przytrzymaj Ctrl, jednocześnie klikając Odśwież, lub naciśnij klawisze Ctrl+F5
- Opera: Naciśnij klawisze Ctrl+F5.
window.gadget_reviewex = {
api: new mw.Api(),
or_continue: null,
async_done: 0,
DiffData: {},
review: function(info, button, comment)
{
parameters = {
action: 'review',
revid: info.revid
};
if(comment)
{
parameters.comment = comment;
}
$('#RevisionCard-'+info.revid).css('cursor', 'wait');
this.api.postWithEditToken(parameters)
.done( function(result)
{
if (result.review.result == "Success")
{
$('#RevisionCard-'+info.revid+' .diff-display').hide();
$('#RevisionCard-'+info.revid).css('cursor', 'revert').addClass('reviewed').append('<big>OZNACZONO JAKO PRZEJRZANE</big>');
button.setDisabled(true);
}
else
{
alert("Status inny niż pomyślny?");
}
})
.fail(function(code, result)
{
alert("Błąd podczas oznaczania.");
console.log(code, result);
//dodać obsługę "ktoś przejrzał"
});
},
undo: function(info, button, reason)
{
parameters = {
action: 'edit',
pageid: info.pageid,
undo: info.revid,
undoafter: info.stable_revid,
/*baserevid: info.stable_revid,*/
summary: mw.messages.get('Revert_summary')+' '+info.stable_revid+"."
};
if(reason)
{
parameters.summary += " Powód: "+reason;
}
$('#RevisionCard-'+info.revid).css('cursor', 'wait');
this.api.postWithEditToken(parameters)
.done(function(result)
{
message = (typeof result.edit.nochange == "undefined") ? "Wycofano widoczne niżej edycje. Można kontynuować pracę." : "Nie zapisano żadnych zmian. Pusty diff lub błąd lub konflikt edycji.";
$('#RevisionCard-'+info.revid+' table').before('<big>'+message+'</big>');
button.setDisabled(true);
})
.fail(function(code, result)
{
if(result.error.code == "editconflict")
{
alert("Konflikt edycji.");
}
else
{
alert("Błąd podczas cofania.");
}
console.log(result);
})
.always(function(code, result)
{
$('#RevisionCard-'+info.revid).css('cursor', 'revert');
});
},
clickable_links: function(content)
{
//<nowiki>
content = content.replace(/(\b(https?|):\/\/[-A-Z0-9+&@#\/%?=~_|!:,.;]*[-A-Z0-9+&@#\/%=~_|])/ig, '<a href="$1" target="_blank">$1</a>');
content = content.replace(/(^|[^\/])(www\.[\S]+(\b|$))/gim, '$1<a target="_blank" href="http://$2">$2</a>');
content = content.replace(/([^\[])\[{2}([^\[\]\|\\<\>\n]*)([^\[\]\\<\>\n]*?)?\]{2}([^\]])/g, '$1<a class="autolink" target="_blank" href="/wiki/$2">[[$2$3]]</a>$4');//wikilink
content = content.replace(/([^\{])\{{2}(subst\:|msg\:)?([^\#\{\}\|\\<\>\n]*)([^\#\{\}\\<\>\n]*?)?\}{2}([^\}])/g, '$1<a class="autolink" target="_blank" href="/wiki/Template:$3">{{$2$3$4}}</a>$5');//szablon
//</nowiki>
return content;
},
VisualDiff: function(rev1, rev2, title, targetSelector)
{
mw.loader.using('ext.visualEditor.diffLoader', function(){
modulePromise = mw.loader.using(['ext.visualEditor.articleTarget']);
mw.libs.ve.diffLoader.getVisualDiffGeneratorPromise(rev1, rev2, modulePromise, title, title).then( function (visualDiffGenerator) {
diffElement = new ve.ui.DiffElement(visualDiffGenerator(), {classes: ['ve-init-mw-diffPage-diff']});
$(targetSelector).html(diffElement.$element).parent().css('cursor', 'revert');
});
});
},
display_results: function()
{
$('#diffs').html('');
var that = this;
$.each(this.DiffData, function(LastRevId, info) {
title = info.revinfo.title;
article_links = '<a href="'+mw.util.getUrl(title)+'" target="_BLANK">'+title+'</a> '+
'<span class="article-actions"><a href="'+mw.util.getUrl(title, {action: 'edit'})+'" target="_BLANK">edytuj</a> | <a href="'+mw.util.getUrl(title, {action: 'history'})+'" target="_BLANK" class="reviewex-link-history">historia</a> | <a href="'+mw.util.getUrl(title, {diff: info.revinfo.revid, oldid: info.revinfo.stable_revid})+'" target="_BLANK" class="reviewex-link-diff" title="Otwórz porównanie w nowym oknie">porównanie</a></span>';
$('#diffs').prepend('<div class="RevisionCard" id="RevisionCard-'+LastRevId+'"><h2>'+article_links+'</h2>'+
'<table class="diff diff-display">'+
'<colgroup><col class="diff-marker"><col class="diff-content"><col class="diff-marker"><col class="diff-content"></colgroup>'+
'<tbody>'+info.diff.compare['*']+'</tbody>'+
'</table></div>');
var bAccept = new OO.ui.ButtonWidget({label: 'Oznacz jako przejrzane', icon: 'check'});
bAccept.$element.on('click', function(e){
if(e.originalEvent.shiftKey) OO.ui.prompt('Dodaj komentarz do logu oznaczania').done(function(comment){
if (comment !== null) that.review(info.revinfo, bAccept, comment);
}); else that.review(info.revinfo, bAccept);
}).addClass('reviewbutton');
var bRevert = new OO.ui.ButtonWidget({label: 'Wycofaj zmiany', icon: 'undo', flags: ['destructive']});
bRevert.$element.on('click', function(e){
if(e.originalEvent.shiftKey) OO.ui.prompt('Podaj powód wycofania').done(function(comment){
if (comment !== null) that.undo(info.revinfo, bRevert, comment);
}); else that.undo(info.revinfo, bRevert);
}).addClass('revertbutton');
$('#RevisionCard-'+LastRevId+' table').before(bAccept.$element).before(bRevert.$element);
var bVisualDiff = new OO.ui.ToggleButtonWidget({label: 'V/T', icon: 'articles', title: 'Przełącz na widok porównania wizualny/wikikodu'});
bVisualDiff.on('click', function(e){
var parentId = '#RevisionCard-'+LastRevId;
if ($(parentId+' .visualdiff').length)
{
$(parentId+' .visualdiff').toggle();
$(parentId+' .diff').toggle();
return;
}
$(parentId+' .diff').before('<div class="visualdiff diff-display">ładowanie</div>').hide();
$(parentId).css('cursor', 'wait');
that.VisualDiff(info.revinfo.stable_revid, info.revinfo.revid, info.revinfo.title, parentId+' .visualdiff');
});
bVisualDiff.$element.addClass('vetoggle');
$('#RevisionCard-'+LastRevId+' .revertbutton').after(bVisualDiff.$element);
});
if($('#clickable_links').prop('checked')) $('.diff-context, .diff-addedline, .diff-deletedline').each(function(n, elem){
content = $(elem).html();
content = that.clickable_links(content);
$(elem).html(content);
});
$('.reviewex-link-history').click(function(e){
if(e.originalEvent.shiftKey)
{
e.preventDefault();
var parentId = e.target.parentNode.parentNode.parentNode.id;
var revision = parentId.split('-', 2)[1];
var pageid = that.DiffData[revision].revinfo.pageid;
$('#'+parentId+' .reviewex-history-preview').remove();
$('#'+parentId+' .diff').before('<div class="reviewex-history-preview"><h3>Historia edycji - ostatnie 10</h3><div>czekaj...</div></div>');
var request = {
"action": "query",
"format": "json",
"prop": "flagged|revisions",
"rvprop": "ids|timestamp|flags|parsedcomment|user|flagged",
"pageids": pageid,
"rvlimit": 10
};
that.api.get(request).done(function(data) {
$('#'+parentId+' .reviewex-history-preview div').html('<table class="wikitable" style="width: 100%"><tr><th>Czas</th><th>User</th><th>Opis</th><th>Przejrzano</th></tr></table>');
revisions = data.query.pages[pageid].revisions;
for(var i = 0; i < revisions.length; i++)
{
r = revisions[i];
fl = (typeof r.flagged === "object") ? '<a href="'+mw.util.getUrl("special:contribs/"+r.flagged.user)+'" target="_BLANK">'+r.flagged.user+'</a>' : 'NIE';
$('#'+parentId+' .reviewex-history-preview table').append('<tr><td>'+r.timestamp+'</td><td><a href='+mw.util.getUrl("special:contribs/"+r.user)+' target="_BLANK" class="reviewex-user-contribs-link">'+r.user+'</a></td><td>'+r.parsedcomment+'</td><td>'+fl+'</td></tr>');
}
$('#'+parentId+' .reviewex-user-contribs-link').click(function(e){
if(e.originalEvent.shiftKey)
{
e.preventDefault();
var username = e.target.text;
$('#'+parentId+' .reviewex-contribs-preview').remove();
$('#'+parentId+' .reviewex-history-preview').before('<div class="reviewex-contribs-preview"><h3>Ostatnie 10 edycji użytkownika '+username+'</h3><div></div></div>');
that.api.get({action: "query", list: "usercontribs", ucuser: username, ucprop: 'ids|title|timestamp|parsedcomment|patrolled'}).done(function(data) {
contribs = data.query.usercontribs;
$('#'+parentId+' .reviewex-contribs-preview div').html('<table class="wikitable" style="width: 100%"><tr><th>Czas</th><th>Strona</th><th>Opis</th><th>Przejrzano</th></tr></table>');
for(var i = 0; i < contribs.length; i++)
{
r = contribs[i];
fl = (typeof r.patrolled !== 'undefined' ? (typeof r.autopatrolled !== 'undefined' ? 'TAK (A)' : 'TAK' ) : 'NIE');
$('#'+parentId+' .reviewex-contribs-preview table').append('<tr><td>'+r.timestamp+'</td><td><a href='+mw.util.getUrl(r.title)+' target="_BLANK">'+r.title+'</a></td><td>'+r.parsedcomment+'</td><td>'+fl+'</td></tr>');
}
});
}
});
});
}
});
$('#diffs').css('cursor', 'revert');
},
diff: function(waiting_revision_info, max)
{
var that = this;
if (this.async_done === 0) this.DiffData = {};
this.api.get({action: 'compare', fromrev: waiting_revision_info.stable_revid, torev: waiting_revision_info.revid}).done(function(diff)
{
that.DiffData[waiting_revision_info.revid] = {"revinfo": waiting_revision_info, "diff": diff};
that.async_done++;
if(that.async_done == max)
{
that.display_results();
}
});
},
getList: function(nav)
{
if($('#category').val() !== '')
{
alert("Ta funkcja nie działa po wyborze kategorii.");
return;
}
var that = this;
this.async_done = 0;
$('#diffs').html('<span class="reviewex_loading">Pobieranie lub brak danych</span>').css('cursor', 'wait');
$('#reviewEx_nav_prev').hide();
api_params = {
action: 'query',
list: 'oldreviewedpages',
orlimit: $('#orlimit').val(),
ordir: $('input[name=ordir]:checked').val(),
ornamespace: 0
};
if(nav == 'r') this.or_continue = null;
if(this.or_continue !== null) api_params.orstart = this.or_continue;
if($('#ormaxsize').val() !== '') api_params.ormaxsize = $('#ormaxsize').val();
if($('#only_watched').prop('checked')) api_params.orfilterwatched = 'watched';
this.api.get(api_params).done(function(data) {
var entries = data.query.oldreviewedpages;
for(i = 0; i < entries.length; i++)
{
that.diff(entries[i], entries.length);
}
if(typeof data.continue !== 'undefined')
{
that.or_continue = data.continue.orstart;
$('reviewEx_nav_next').attr('disabled', false);
}
else
{
that.or_continue = null;
}
if(that.or_continue === null)
{
$('reviewEx_nav_next').attr('disabled');
}
if(nav == 'n')
{
$('reviewEx_nav_prev').attr('disabled', false);
}
});
},
getListFromCategory: function(nav)
{
var category = mw.util.rawurlencode($('#category').val()).replace('%7C', '%0A');//| na nowa_linia
var category_n = mw.util.rawurlencode($('#category_n').val()).replace('%7C', '%0A');
var depth = $('#depth').val();
var sort = ($('input[name=ordir]:checked').val() == "older") ? "descending" : "ascending";
var limit = $('#orlimit').val();
if (nav == 'r')
{
this.or_continue = null;
$('#reviewEx_nav_prev').hide();
}
var site = mw.config.get('wgServerName').split('.', 3);
var project = site[1];
var language = (site[2] != 'beta') ? site[0] : 'pl';
var negcats = (category_n) ? '&negcats='+category_n : '';
var that = this;
this.async_done = 0;
$('#diffs').html('<span class="reviewex_loading">Pobieranie lub brak danych</span>').css('cursor', 'wait');
var continuation = '';
if(typeof this.or_continue === "object" && this.or_continue != null)
{
continuation = '&'+((sort == "descending" && nav != 'p') ? 'before' : 'after')+'='+this.or_continue[nav];
$('#reviewEx_nav_prev').show();
}
$.ajax({
url: "https://petscan.wmflabs.org/?depth="+depth+"&combination=union&edits%5Bflagged%5D=no&edits%5Bbots%5D=both&ns%5B0%5D=1&format=json&sortby=date&project="+project+"&sortorder="+sort+"&language="+language+"&edits%5Banons%5D=both&categories="+category+"&output_limit="+limit+"&doit="+continuation+negcats,
dataType: 'jsonp'
}).done(function(petscan_results){
var results = petscan_results['*'][0].a['*'];
var ids = [];
var nResults = results.length;
for (var i = 0; i < nResults; i++)
{
ids[i] = results[i].id;
}
var request = {
"action": "query",
"format": "json",
"prop": "flagged|revisions",
"pageids": ids.join('|'),
"rvprop": "ids|timestamp|flags|comment|user|flagged"
};
that.api.get(request).done(function(data) {
$.each(data.query.pages, function(pageId, info) {
var entry = {
pageid: pageId,
title: info.title,
revid: info.revisions[0].revid,
stable_revid: info.flagged.stable_revid
};
that.diff(entry, nResults);
});
});
that.or_continue = {p: results[0].touched, n: results[nResults-1].touched};
});
},
prepare_window: function()
{
function MyDialog( config ) {
MyDialog.super.call( this, config );
}
OO.inheritClass( MyDialog, OO.ui.ProcessDialog );
MyDialog.static.name = 'myDialog';
MyDialog.static.title = 'Informacje';
MyDialog.static.actions = [
{
label: 'Zamknij',
flags: 'safe'
}
];
MyDialog.prototype.getActionProcess = function ( action ) {
var dialog = this;
if ( action ) {
return new OO.ui.Process( function () {
dialog.close( {
action: action
} );
} );
}
return MyDialog.super.prototype.getActionProcess.call( this, action );
};
MyDialog.prototype.initialize = function () {
MyDialog.super.prototype.initialize.call( this );
this.content = new OO.ui.PanelLayout( {
padded: true,
expanded: false
} );
this.content.$element.append( '<div id="reviewex-popup-content">' );
this.$body.append( this.content.$element );
};
MyDialog.prototype.getBodyHeight = function () {
return this.content.$element.outerHeight( true );
};
this.myDialog = new MyDialog( {
size: 'medium'
} );
this.windowManager = new OO.ui.WindowManager();
$( document.body ).append( this.windowManager.$element );
this.windowManager.addWindows( [ this.myDialog ] );
},
open_help_window: function (name)
{
this.windowManager.openWindow(this.myDialog);
$('#reviewex-popup-content').html(this.reviewex_infos[name]);
},
reviewex_infos: {
rt: '<h3>Narzędzia pomagające w oznaczaniu</h3>'+
'<ul><li><a href="'+mw.util.getUrl('Special:ValidationStatistics')+'" target="_blank">Statystyki nieprzejrzanych</a></li><li><a href="http://tools.wikimedia.pl/~masti/review.html" target="_blank">Statystyki redaktorów</a></li><li><a href="https://tools.wmflabs.org/review-stats/reviewers.php" target="_blank">Statystyki redaktorów 2</a></li><li><a href="'+mw.util.getUrl('Special:Log/review')+'" target="_blank">Rejestr</a></li><li><a href="https://tools.wmflabs.org/sighting/deep_out_of_sight.php?language=pl" target="_blank">Z kategorii</a></li><li><a href="http://petscan.wmflabs.org/?ns%5B0%5D=1&project=wikipedia&interface_language=pl&depth=5&language=pl&edits%5Bflagged%5D=no" target="_blank">Z kategorii (petscan)</a></li></ul><br />'+
''
},
reviewEx_template: ''+
'<style>.RevisionCard {border: 3px solid; border-color: lightseagreen;} .RevisionCard:nth-child(even) {border-color: lightskyblue;} .reviewbutton {float: right;} .reviewed {border: 2px solid gray !important;} .reviewEx_nav button {border-color: red; background-color: white; border-width: 2px; padding: 5px 20px 5px 20px;} .article-actions{font-size: smaller; float: right; margin-right: 0.5em;}</style>'+
'Sortuj: <label><input type="radio" name="ordir" value="newer" />Od najstarszych</label> <label><input type="radio" name="ordir" value="older" checked />Od najnowszych</label> '+
'| Maksymalna różnica znaków: <input id="ormaxsize" size="3" /> | <label><input type="checkbox" id="only_watched" />Tylko obserwowane</label>, lub<hr />'+
'Kategorie: <input id="category" title="Wpisz nazwę kategorii, bez prefiksu. Dane będą pobierane z zewnętrznego narzędzia. Powyższe opcje nie będą działać, inne mogą działać różnie." /> Głębokość: <input id="depth" size="3" /> Wyklucz podkategorie: <input id="category_n" /> [separator nazw: <b>|</b>]<hr />'+
'Wyników na stronie: <input id="orlimit" size="3" value="50" /> <label title="Kody wikilinków i szablonów oraz adresy URL http staną się klikalne. Otwierane w nowym oknie."><input type="checkbox" id="clickable_links" checked />Klikalne linki</label>'+
'<span style="float:right">(<a href="https://pl.wikipedia.org/wiki/Wikipedysta:Wargo/Skrypty#Panel_oznaczania" target="_BLANK">pomoc</a> | <a id="reviewtools">inne narzędzia</a>)</span>'+
'<div id="diffs"></div>'+
'<div style="text-align: center" class="reviewEx_nav">'+
' <button id="reviewEx_nav_prev">Poprzednie</a>'+
' <button id="reviewEx_nav_next">Następne</a>'+
'</div>',
init: function()
{
var that = this;
$.when(mw.loader.using(['mediawiki.diff.styles', 'oojs-ui-windows', 'oojs-ui-widgets', 'oojs-ui.styles.icons-editing-core', 'oojs-ui.styles.icons-interactions', 'oojs-ui.styles.icons-content'])).then(function(){
$('#firstHeading').text('Panel moderacji');
$('#mw-content-text').html(that.reviewEx_template);
var bLoad = new OO.ui.ButtonWidget({label: 'Pokaż'});
bLoad.$element.on('click', function(e){
that['getList'+($('#category').val() !== '' ? 'FromCategory' : '')]('r');
});
$('#orlimit').after(bLoad.$element);
$('#reviewEx_nav_next, #reviewEx_nav_prev').click(function(e){
e.preventDefault();
that['getList'+($('#category').val() !== '' ? 'FromCategory' : '')]((e.target.id == 'reviewEx_nav_next') ? 'n' : 'p');
});
that.prepare_window();
$('#reviewtools').click(function(e){
e.preventDefault();
that.open_help_window('rt');
});
that.getList();
});
}
};
$.when(mw.loader.using(['mediawiki.api', 'mediawiki.jqueryMsg']), $.ready).then(function() {
var messages = {
pl: {
"Revert_summary": "Przywrócono wersję",
"Specialpage": "Specjalna:Pusta_strona",
},
en: {
"Revert_summary": "Restored version",
"Specialpage": "Special:BlankPage",
},
};
mw.messages.set(messages[mw.config.get('wgContentLanguage')]);
if(mw.config.get('wgPageName') == mw.messages.get('Specialpage')+'/ReviewEx')
{
window.gadget_reviewex.init();
}
mw.util.addPortletLink('p-tb', "/wiki/"+mw.messages.get('Specialpage')+"/ReviewEx", 'Panel oznaczania');
});