User:Makecat/wikidata useful-zh.js

From Wikidata
Jump to navigation Jump to search

Note: After publishing, you may have to bypass your browser's cache to see the changes.

  • Firefox / Safari: Hold Shift while clicking Reload, or press either Ctrl-F5 or Ctrl-R (⌘-R on a Mac)
  • Google Chrome: Press Ctrl-Shift-R (⌘-Shift-R on a Mac)
  • Edge: Hold Ctrl while clicking Refresh, or press Ctrl-F5.
/*
USAGE : Add the line
importScript("User:Magnus Manske/wikidata useful.js");// [[User:Magnus Manske/wikidata useful.js]]
to your [[Special:Mypage/common.js]] page
*/

/************************************************************************************************************************
The section below contains the "Wikidata Usefuls" link definitions. Add new ones or edit existing ones as you see fit.
*************************************************************************************************************************/

var wd_useful_thisis = [
	[
		{
			pre : '人:' ,
			options : [
				[ '<b>人</b>' , 'p107:q215627' ] ,
				[ '男性' , 'p107:q215627' , 'p21:q6581097' ] ,
				[ '女性' , 'p107:q215627' , 'p21:q6581072' ] ,
			]
		} ,
		
		{
			pre : '职业:' ,
			options : [
				[ '演员' , 'p106:q33999' ] ,
				[ '歌手' , 'p106:q177220' ] ,
				[ '律师' , 'p106:q40348' ] ,
				[ '作家' , 'p106:q36180' ] ,
				[ '画家' , 'p106:q1028181' ] ,
				[ '雕塑家' , 'p106:q1281618' ] ,
				[ '政治家' , 'p106:q82955' ] ,
				[ '音乐家' , 'p106:q639669' ] ,
				[ '导演' , 'p106:q2526255' ] ,
			]
		} ,
		
		{
			pre : '体育:' ,
			options : [
				[ '运动员' , 'p106:q2066131' ] ,
				[ '篮球' , 'p106:q3665646' ] ,
				[ '足球' , 'p106:q937857' ] ,
				[ '板球' , 'p106:q5185059' ] ,
			]
		} ,
		
		{
			pre : '生物:' ,
			options : [
				[ '物种' , 'p105:q7432' , 'p107:q1969448' ] ,
				[ '属' , 'p105:q34740' , 'p107:q1969448' ] ,
				[ '科' , 'p105:q35409' , 'p107:q1969448' ] ,
				[ '目' , 'p105:q36602' , 'p107:q1969448' ] ,
				[ '纲' , 'p105:q37517' , 'p107:q1969448' ] ,
			]
		} ,
		
		{
			pre : '地理:' ,
			options : [
				[ '<b>地点</b>' , 'p107:q618123' ] ,
				[ '村' , 'p107:q618123', 'p132:q532' ] ,
				[ '镇' , 'p107:q618123', 'p132:q3957' ] ,
				[ '乡' , 'p107:q618123', 'p132:q1500350' ] ,
				[ '市' , 'p107:q618123', 'p132:q515' ] ,
				[ '区' , 'p107:q618123', 'p132:q149621' ] ,
				[ '直辖市' , 'p107:q618123', 'p132:q15284' ] ,
				[ '省' , 'p107:q618123', 'p132:q34876' ] ,
				//[ '部' , 'p107:q618123', 'p132:q643589' ] ,
				[ '县' , 'p107:q618123', 'p132:q706447' ] ,
				[ '河' , 'p107:q618123', 'p31:q4022' ] ,
				[ '湖' , 'p107:q618123', 'p31:q23397' ] ,
				[ '火车站' , 'p107:q618123', 'p31:q55488' ] ,
			]
		} ,
		
		{
			pre : '作品:' ,
			options : [
				[ '<b>作品</b>' , 'p107:q386724' ] ,
				[ '电影' , 'p107:q386724' , 'p31:q11424' ] ,
				[ '唱片' , 'p107:q386724' , 'p31:q482994' ] ,
				[ '歌曲' , 'p107:q386724' , 'p31:q7366' ] ,
				[ '书籍' , 'p107:q386724' , 'p31:q571' ] ,
				[ '小说' , 'p107:q386724' , 'p31:q571' , 'p136:q8261' ] ,
				[ '虚构角色' , 'p107:q386724' , 'p31:q95074' ] ,
				[ '电子游戏' , 'p107:q386724' , 'p31:q7889' ] ,
			]
		} ,

		{
			pre : '团体:' ,
			options : [
				[ '<b>组织</b>' , 'p107:q43229' ] ,
				[ '乐队' , 'p107:q43229' , 'p31: q215380' ] ,
				[ '摇滚乐队' , 'p107:q43229' , 'p31: q5741069' ] ,
			]
		} ,
		
		{
			pre : '其他:' ,
			options : [
				[ '<b>事件</b>' , 'p107:q1656682' ] ,
				[ '<b>术语</b>' , 'p107:q1969448' ] ,
				[ '<b>消歧义</b>' , 'p107:q4167410' ] ,
			]
		} ,
		
	]
] ;

/************************************************************************************************************************
The section below contains the "Wikidata Usefuls" country list. Add new ones or edit existing ones as you see fit.
*************************************************************************************************************************/

var wd_useful_countries = {
	"Afghanistan" : "q889",
	"Albania" : "q222",
	"Algeria" : "q262",
	"Andorra" : "q228",
	"Angola" : "q916",
	"Antigua and Barbuda" : "q781",
	"Argentina" : "q414",
	"Armenia" : "q399",
	"Australia" : "q408",
	"Austria" : "q40",
	"Azerbaijan" : "q227",
	"Bahamas" : "q778",
	"Bahrain" : "q398",
	"Bangladesh" : "q902",
	"Barbados" : "q244",
	"Belarus" : "q184",
	"Belgium" : "q31",
	"Belize" : "q242",
	"Benin" : "q962",
	"Bhutan" : "q917",
	"Bolivia" : "q750",
	"Bosnia and Herzegovina" : "q225",
	"Botswana" : "q963",
	"Brazil" : "q155",
	"Brunei" : "q921",
	"Bulgaria" : "q219",
	"Burkina Faso" : "q965",
	"Burundi" : "q967",
	"Cambodia" : "q424",
	"Cameroon" : "q1009",
	"Canada" : "q16",
	"Cape Verde" : "q1011",
	"Central African Republic" : "q929",
	"Chad" : "q657",
	"Chile" : "q298",
	"China" : "q148",
	"Colombia" : "q739",
	"Comoros" : "q970",
	"Costa Rica" : "q800",
	"Côte d'Ivoire" : "q1008",
	"Croatia" : "q224",
	"Cuba" : "q241",
	"Cyprus" : "q229",
	"Czech Republic" : "q213",
	"Democratic Republic of the Congo" : "q974",
	"Denmark" : "q35",
	"Djibouti" : "q977",
	"Dominica" : "q784",
	"Dominican Republic" : "q786",
	"East Timor" : "q574",
	"Ecuador" : "q736",
	"Egypt" : "q79",
	"El Salvador" : "q792",
	"Equatorial Guinea" : "q983",
	"Eritrea" : "q986",
	"Estonia" : "q191",
	"Ethiopia" : "q115",
	"Federated States of Micronesia" : "q702",
	"Fiji" : "q712",
	"Finland" : "q33",
	"France" : "q142",
	"Gabon" : "q1000",
	"Gambia" : "q1005",
	"Georgia" : "q230",
	"Germany" : "q183",
	"Ghana" : "q117",
	"Greece" : "q41",
	"Grenada" : "q769",
	"Guatemala" : "q774",
	"Guinea" : "q1006",
	"Guinea-Bissau" : "q1007",
	"Guyana" : "q734",
	"Haiti" : "q790",
	"Honduras" : "q783",
	"Hungary" : "q28",
	"Iceland" : "q189",
	"India" : "q668",
	"Indonesia" : "q252",
	"Iran" : "q794",
	"Iraq" : "q796",
	"Ireland" : "q27",
	"Israel" : "q801",
	"Italy" : "q38",
	"Jamaica" : "q766",
	"Japan" : "q17",
	"Jordan" : "q810",
	"Kazakhstan" : "q232",
	"Kenya" : "q114",
	"Kiribati" : "q710",
	"Kuwait" : "q817",
	"Kyrgyzstan" : "q813",
	"Laos" : "q819",
	"Latvia" : "q211",
	"Lebanon" : "q822",
	"Lesotho" : "q1013",
	"Liberia" : "q1014",
	"Libya" : "q1016",
	"Liechtenstein" : "q347",
	"Lithuania" : "q37",
	"Luxembourg" : "q32",
	"Macedonia" : "q221",
	"Madagascar" : "q1019",
	"Malawi" : "q1020",
	"Malaysia" : "q833",
	"Maldives" : "q826",
	"Mali" : "q912",
	"Malta" : "q233",
	"Marshall Islands" : "q709",
	"Mauritania" : "q1025",
	"Mauritius" : "q1027",
	"Mexico" : "q96",
	"Moldova" : "q217",
	"Mongolia" : "q711",
	"Montenegro" : "q236",
	"Monaco" : "q235",
	"Morocco" : "q1028",
	"Mozambique" : "q1029",
	"Myanmar" : "q836",
	"Namibia" : "q1030",
	"Nauru" : "q697",
	"Nepal" : "q837",
	"Netherlands" : "q55",
	"New Zealand" : "q664",
	"Nicaragua" : "q811",
	"Niger" : "q1032",
	"Nigeria" : "q1033",
	"North Korea" : "q423",
	"Norway" : "q20",
	"Oman" : "q842",
	"Pakistan" : "q843",
	"Palau" : "q695",
	"Panama" : "q804",
	"Papua New Guinea" : "q691",
	"Paraguay" : "q733",
	"Peru" : "q419",
	"Philippines" : "q928",
	"Poland" : "q36",
	"Portugal" : "q45",
	"Qatar" : "q846",
	"Republic of the Congo" : "q971",
	"Romania" : "q218",
	"Russia" : "q159",
	"Rwanda" : "q1037",
	"Saint Kitts and Nevis" : "q763",
	"Saint Lucia" : "q760",
	"Saint Vincent and the Grenadines" : "q757",
	"Samoa" : "q683",
	"San Marino" : "q238",
	"São Tomé and Príncipe" : "q1039",
	"Saudi Arabia" : "q851",
	"Senegal" : "q1041",
	"Serbia" : "q403",
	"Seychelles" : "q1042",
	"Sierra Leone" : "q1044",
	"Singapore" : "q334",
	"Slovakia" : "q214",
	"Slovenia" : "q215",
	"Solomon Islands" : "q685",
	"Somalia" : "q1045",
	"South Africa" : "q258",
	"South Korea" : "q884",
	"South Sudan" : "q958",
	"Spain" : "q29",
	"Sri Lanka" : "q854",
	"Sudan" : "q1049",
	"Suriname" : "q730",
	"Swaziland" : "q1050",
	"Sweden" : "q34",
	"Switzerland" : "q39",
	"Syria" : "q858",
	"Tajikistan" : "q863",
	"Tanzania" : "q924",
	"Thailand" : "q869",
	"Togo" : "q945",
	"Tonga" : "q678",
	"Trinidad and Tobago" : "q754",
	"Tunisia" : "q948",
	"Turkey" : "q43",
	"Turkmenistan" : "q874",
	"Tuvalu" : "q672",
	"Uganda" : "q1036",
	"Ukraine" : "q212",
	"United Arab Emirates" : "q878",
	"United Kingdom" : "q145",
	"United States" : "q30",
	"Uruguay" : "q77",
	"Uzbekistan" : "q265",
	"Vanuatu" : "q686",
	"Vatican City" : "q237",
	"Venezuela" : "q717",
	"Vietnam" : "q881",
	"Yemen" : "q805",
	"Zambia" : "q953",
	"Zimbabwe" : "q954"
} ;

/************************************************************************************************************************
DO NOT EDIT BELOW THIS LINE UNLESS YOU REALLY KNOW WHAT YOU ARE DOING!
*************************************************************************************************************************/



function ucFirst(string) {
	return string.substring(0, 1).toUpperCase() + string.substring(1);
}


var wd_useful = {

	id_cnt : 0 ,
	api : '/w/api.php' ,
	link2data : [] ,
	
	countries : {} ,
	
	addPropsFromLink : function ( o ) {
		var self = this ;
		var lid = $(o).attr('lid') ;
//		console.log ( self.link2data[lid] ) ;
		var is_running = self.queue.length > 0 ;
		$.each ( self.link2data[lid]||[] , function ( k , v ) {
			var pq = v.split ( ':' ) ;
			if ( pq.length != 2 ) {
				console.log ( "PROBLEM : " + v ) ;
				return ;
			}
			self.queue.push ( { mode:'set' , prop:pq[0] , target_entity:pq[1] } ) ;
		} ) ;
		if ( !is_running ) {
			self.processed = 0 ;
			self.processNextQueueItem () ;
		}
		return false ;


	} ,

	init : function () {
		var self = this ;
		var q = mw.config.get('wgPageName').toLowerCase() ;
		self.q = q ;
		self.queue = [] ;
		
		var h = "<div id='wd_useful_dialog'>" ;
		
		h += "<div>" ;
//		h += "This is:" ;
		
		var lid = 0 ;
		var maxw = 320 ;
		$.each ( wd_useful_thisis , function ( k1 , v1 ) {
			h += "<div style='margin-bottom:5px'>" ;
			$.each ( v1 , function ( k2 , v2 ) {
				var indent = k2 == 0 ? 10 : 15 ;
				h += "<div style='max-width:"+maxw+"px;text-indent:-10px;margin-left:"+indent+"px;margin-bottom:3px'>" ;
				if ( v2.pre !== undefined ) h += v2.pre ;
				$.each ( v2.options , function ( k3 , v3 ) {
					var title = v3.shift() ;
					self.link2data[lid] = v3 ;
					var h2 = "<a href='#' lid='" + lid + "' onclick='wd_useful.addPropsFromLink(this);return false;'>" + title + "</a>" ;
					if ( k3+1 < v2.options.length ) h2 += '/' ;
					h += "<nobr>" + h2 + '</nobr>' ;
					h += '<wbr/>' ;
					lid++ ;
				} ) ;
				if ( v2.post !== undefined ) h += v2.post ;
				h += "</div>" ;
			} ) ;
			h += "</div>" ;
		} ) ;

		h += "<hr/>" ;
		h += "<a href='#' onclick='$(\"#country\").val(\"q148\");return false'>中</a>" ;
		h += "|<a href='#' onclick='$(\"#country\").val(\"q30\");return false'>美</a>" ;
		h += "|<a href='#' onclick='$(\"#country\").val(\"q145\");return false'>英</a>" ;
		h += "|<a href='#' onclick='$(\"#country\").val(\"q183\");return false'>德</a>" ;
		h += "|<a href='#' onclick='$(\"#country\").val(\"q142\");return false'>法</a>" ;
		h += "|<a href='#' onclick='$(\"#country\").val(\"q29\");return false'>西</a>" ;
		h += "|<a href='#' onclick='$(\"#country\").val(\"q38\");return false'>意</a>" ;
		h += "<br/><select id='country'></select>" ;
		h += "<br/>" ;
		h += "<a href='#' onclick='wd_useful.useCountry(0);return false'>国家</a> | " ;
		h += "<a href='#' onclick='wd_useful.useCountry(1);return false'>国籍</a>" ;
		h += "<hr/>" ;
		h += "<div><a href='#' onclick='wd_useful.duplicateStatements();return false'>将声明复制到中文维基分类的所有项目</a></div>" ;
		h += "<div><a href='#' onclick='wd_useful.duplicateStatementsFromItemList();return false'>将声明复制到一个页面上的所有项目</a></div>" ;
		h += "</div>" ;
		
		h += "</div>" ;
		$('#mw-content-text').append ( h ) ;
		
		var main = $('#wb-item-'+self.q.toLowerCase()) ;
		$('#wd_useful_dialog').dialog ( {
			modal : false ,
			title : 'Wikidata Usefuls' ,
			width : 'auto' ,
			position : { my: "left top", at: "right top", of: main } ,
			open: function( event, ui ) {
				$('#wd_useful_dialog a').css ( { color:'#0b0080' } ) ;
				main.focus() ;
			}
		} ) ;
		$('#wd_useful_dialog a').blur();
		self.loadCountries () ;
		self.tryDesc() ;
		self.autoName() ;
		self.tryAutoAdd() ;
		self.autoRenameStatements () ;
		self.showQ() ;
	} ,
	
	autoRenameStatements : function () {
		var self = this ;
		entity = 'q' + self.q.replace ( /\D/g , '' ) ;
		$.getJSON ( self.api , {
			action : 'wbgetentities' ,
			format : 'json' ,
			ids : entity ,
			props : 'info|claims'
		} , function ( data ) {
			if ( undefined === data.entities[entity] ) return ;
			if ( undefined === data.entities[entity].claims ) return ;
			$.each ( data.entities[entity].claims , function ( p , v ) {
				if ( p=='p28'|p=='p11'||p=='p12'||p=='p28'||p=='p83'||p=='p34' ) { // replacing deprecated properties with "located in administrative unit"
					self.replaceClaimProperty ( { old_prop : p , new_prop : 'p131' , claim : v } ) ;
				}
			} ) ;
			self.processNextQueueItem () ;
		} ) ;
	} ,
	
	replaceClaimProperty : function ( data ) {
		var self = this ;
		$.each ( data.claim , function ( k , v ) {
			var nid = v.mainsnak.datavalue.value['numeric-id'] ;
//			console.log ( data.old_prop + " => " + data.new_prop + " : " + nid ) ;
			self.queue.push ( { mode:'set' , prop:data.new_prop , target_entity:'q'+nid } ) ;
			self.queue.push ( { mode:'remove' , prop:data.old_prop , target_entity:'q'+nid } ) ;
		} ) ;
	} ,
	
	showQ : function () {
		$('div.valueview-value a').each ( function ( k , v ) {
			var url = $(v).attr('href') || '' ;
			var m = url.match ( /\/[qQ](\d+)$/ ) ;
			if ( m != null ) {
				var h = " <span style='color:#999999'><i>q" + m[1] + "</i></span>" ;
				$(v).after ( h ) ;
			}
		} ) ;
	} ,
	
	duplicateStatementsFromItemList : function () {
		var self = this ;
		var lang = 'zh' ;
		var name = prompt("输入维基数据上的项目列表:", "");//'Wikidata:Tropical cyclones task force/standard/Atlantic' ;
		if ( name == null ) return ;
		self.dupCount = 0 ;
		self.processed = 0 ;
		self.claims = {} ;
		//http://wikidata.org/w/api.php?action=query&prop=links&titles=Wikidata:Tropical%20cyclones%20task%20force/standard/Atlantic&plnamespace=0&pllimit=500&format=jsonfm

		$.getJSON ( self.api , {
				action : 'wbgetentities' ,
				ids : self.q ,
				languages : lang ,
				format : 'json'
			} , function ( d0 ) {
			
				$.each ( d0.entities||[] , function ( k , v ) {
					self.claims = v.claims ;
				} ) ;
			
				$.getJSON ( '//www.wikidata.org/w/api.php?callback=?' , {
					action : 'query' ,
					prop : 'links' ,
					titles : name ,
					plnamespace : 0 ,
					pllimit : 500 ,
					format : 'json'
				} , function ( data ) {
					$.each ( data.query.pages , function ( k1 , v1 ) {
						$.each ( v1.links , function ( k , v ) {
							self.duplicateStatementsToEntity ( v.title ) ;
						} ) ;
					} ) ;
			} ) ;
		} ) ;

	} ,
	
	duplicateStatements : function () {
		var self = this ;
		var lang = 'zh' ;
		var cat = prompt("输入一个中文维基的分类:", "");//'Compositions_by_Pyotr_Ilyich_Tchaikovsky' ;
		if ( cat == null ) return ;
		self.dupCount = 0 ;
		self.processed = 0 ;
		self.claims = {} ;
		
		$.getJSON ( self.api , {
				action : 'wbgetentities' ,
				ids : self.q ,
				languages : lang ,
				format : 'json'
			} , function ( d0 ) {
			
				$.each ( d0.entities||[] , function ( k , v ) {
					self.claims = v.claims ;
				} ) ;
			
				$.getJSON ( '//'+lang+'.wikipedia.org/w/api.php?callback=?' , {
					action : 'query' ,
					list : 'categorymembers' ,
					cmtitle : 'Category:' + cat ,
					cmnamespace : 0 ,
					cmlimit : 500 ,
					format : 'json'
				} , function ( data ) {
					$.each ( data.query.categorymembers , function ( k , v ) {
						var t = v.title ;
						if ( t.match ( /^List[_ ]/ ) ) return ; // No lists!
						self.dupCount++ ;
						$.getJSON ( self.api , {
							action : 'wbgetentities' ,
							sites : lang+'wiki' ,
							titles : t ,
							languages : lang ,
							format : 'json'
						} , function ( d2 ) {
							$.each ( d2.entities||[] , function ( k2 , v2 ) {
//								self.dupCount++ ;
								self.duplicateStatementsToEntity ( k2 , v2 ) ;
							} ) ;
							self.dupCount-- ;
							if ( self.dupCount == 0 ) self.processNextQueueItem() ;
						} ) ;
//						if ( k > 5 ) return false ; // TESTING
					} ) ;
			} ) ;
		} ) ;
	} ,
	
	duplicateStatementsToEntity : function ( q , target ) {
		var self = this ;
		if ( q == self.q || q.replace(/\D/g,'')=='1' ) {
			return ;
		}
		
		$.each ( self.claims , function ( p , v ) {
			var nid = v[0].mainsnak.datavalue.value['numeric-id'] ;
			if ( nid === undefined ) return ;
			var o = { mode:'set' , prop:p , target_entity:'q'+nid , entity:q } ;
			self.queue.push ( o ) ;
		} ) ;

	} ,
	
	tryAutoAdd : function () {
		var self = this ;
		$('.wb-property-container-value .wb-value').each ( function ( k , v ) {
			var t = $(v).text() ;
			if ( t == 'Wikipedia disambiguation page' ) self.isDisambiguation() ;
		} ) ;
	} ,
	
	tryDesc : function () {
		var self = this ;
		var lang ;
		var title ;
		$.each ( ['en','de'] , function ( k , l ) {
			var t = $('.wb-sitelinks-link-'+l+' a').text() ;
			if ( t == '' ) return ;
			lang = l ;
			title = t ;
			return false ;
		} ) ;
		if ( lang === undefined ) return ;
		$.getJSON ( '//'+lang+'.wikipedia.org/w/api.php?callback=?' , {
			action : 'query' ,
			prop : 'extracts' ,
//			exsentences : 5 ,
			exchars : 300 ,
			titles : title ,
			format : 'json'
		} , function ( data ) {
			$.each ( data.query.pages , function ( k , v ) {
				$('table.wb-sitelinks').after ( v.extract ) ;
			} ) ;
		} ) ;
	} ,
	
	useCountry : function ( v ) {
		var self = this ;
		var cq = $('#country').val().replace(/\D/g,'') ;
		var prop = v == 0 ? 17 : 27 ;
//		self.running = true ;
		self.queue.push ( { mode:'set' , prop:'p'+prop , target_entity:'q'+cq } ) ;
//		self.queue.push ( [ 'p'+prop , 'q'+cq ] ) ;
		self.processed = 0 ;
		self.processNextQueueItem () ;
	} ,
	
	loadCountries : function () {
		var self = this ;
		self.countries = wd_useful_countries ;
		//JSON.parse ( "{\"Angola\":\"q916\",\"Botswana\":\"q963\",\"Burkina Faso\":\"q965\",\"Burundi\":\"q967\",\"Comoros\":\"q970\",\"Romania\":\"q218\",\"Republic of the Congo\":\"q971\",\"Democratic Republic of the Congo\":\"q974\",\"Djibouti\":\"q977\",\"Equatorial Guinea\":\"q983\",\"Gabon\":\"q1000\",\"Gambia\":\"q1005\",\"Guinea\":\"q1006\",\"Guinea-Bissau\":\"q1007\",\"Côte d'Ivoire\":\"q1008\",\"Cameroon\":\"q1009\",\"Lesotho\":\"q1013\",\"Liberia\":\"q1014\",\"Madagascar\":\"q1019\",\"Malawi\":\"q1020\",\"Mauritania\":\"q1025\",\"Mauritius\":\"q1027\",\"Morocco\":\"q1028\",\"Mozambique\":\"q1029\",\"Namibia\":\"q1030\",\"Niger\":\"q1032\",\"Nigeria\":\"q1033\",\"Uganda\":\"q1036\",\"Rwanda\":\"q1037\",\"Sao Tomé and Príncipe\":\"q1039\",\"Scotland\":\"q22\",\"Seychelles\":\"q1042\",\"Sierra Leone\":\"q1044\",\"Somalia\":\"q1045\",\"Sudan\":\"q1049\",\"Swaziland\":\"q1050\",\"Soviet Union\":\"q15180\",\"Mexico\":\"q96\",\"Netherlands\":\"q55\",\"Russian Empire\":\"q34266\",\"Egypt\":\"q79\",\"Canada\":\"q16\",\"Timor-Leste\":\"q574\",\"Chad\":\"q657\",\"New Zealand\":\"q664\",\"India\":\"q668\",\"Tonga\":\"q678\",\"Kiribati\":\"q710\",\"Mongolia\":\"q711\",\"Fiji\":\"q712\",\"Suriname\":\"q730\",\"Paraguay\":\"q733\",\"Guyana\":\"q734\",\"Ecuador\":\"q736\",\"Colombia\":\"q739\",\"Bolivia\":\"q750\",\"Saint Vincent and the Grenadines\":\"q757\",\"Saint Lucia\":\"q760\",\"Saint Kitts and Nevis\":\"q763\",\"Jamaica\":\"q766\",\"Grenada\":\"q769\",\"Honduras\":\"q783\",\"Dominica\":\"q784\",\"Dominican Republic\":\"q786\",\"Iran\":\"q794\",\"Iraq\":\"q796\",\"Israel\":\"q801\",\"Panama\":\"q804\",\"Yemen\":\"q805\",\"Jordan\":\"q810\",\"Nicaragua\":\"q811\",\"Kyrgyzstan\":\"q813\",\"Kuwait\":\"q817\",\"Laos\":\"q819\",\"Lebanon\":\"q822\",\"Myanmar\":\"q836\",\"Nepal\":\"q837\",\"Pakistan\":\"q843\",\"Vietnam\":\"q881\",\"South Korea\":\"q884\",\"Afghanistan\":\"q889\",\"Mali\":\"q912\",\"Bhutan\":\"q917\",\"Brunei\":\"q921\",\"Tanzania\":\"q924\",\"Philippines\":\"q928\",\"Central African Republic\":\"q929\",\"Togo\":\"q945\",\"Tunisia\":\"q948\",\"Turkey\":\"q43\",\"Zambia\":\"q953\",\"Zimbabwe\":\"q954\",\"Benin\":\"q962\",\"Japan\":\"q17\",\"Norway\":\"q20\",\"Republic of Ireland\":\"q27\",\"Hungary\":\"q28\",\"Spain\":\"q29\",\"United States of America\":\"q30\",\"Belgium\":\"q31\",\"Luxembourg\":\"q32\",\"Finland\":\"q33\",\"Sweden\":\"q34\",\"Denmark\":\"q35\",\"Poland\":\"q36\",\"Lithuania\":\"q37\",\"Italy\":\"q38\",\"Switzerland\":\"q39\",\"Austria\":\"q40\",\"Greece\":\"q41\",\"Uruguay\":\"q77\",\"Kenya\":\"q114\",\"Ghana\":\"q117\",\"France\":\"q142\",\"United Kingdom\":\"q145\",\"China\":\"q148\",\"Brazil\":\"q155\",\"Russia\":\"q159\",\"Germany\":\"q183\",\"Belarus\":\"q184\",\"Iceland\":\"q189\",\"Estonia\":\"q191\",\"Latvia\":\"q211\",\"Ukraine\":\"q212\",\"Czech Republic\":\"q213\",\"Slovakia\":\"q214\",\"Moldova\":\"q217\",\"Bulgaria\":\"q219\",\"Croatia\":\"q224\",\"Bosnia and Herzegovina\":\"q225\",\"Cyprus\":\"q229\",\"Georgia\":\"q230\",\"Indonesia\":\"q252\",\"South Africa\":\"q258\",\"Uzbekistan\":\"q265\",\"Chile\":\"q298\",\"Singapore\":\"q334\",\"Liechtenstein\":\"q347\",\"Armenia\":\"q399\",\"Serbia\":\"q403\",\"Australia\":\"q408\",\"Argentina\":\"q414\",\"Cambodia\":\"q424\",\"Federated States of Micronesia\":\"q702\"}" ) ;
		self.showCountries() ;
		
		return ;
		$.getJSON ( self.api , {
			action : 'query' ,
			list : 'backlinks' ,
			bltitle : 'Q3624078' ,
			bllimit : 500 ,
			blnamespace : 0 ,
			format : 'json'
		} , function ( data ) {
			var qs = [] ;
			$.each ( data.query.backlinks , function ( k , v ) {
				qs.push ( v.title ) ;
			} ) ;
			var chunk = 50 ;
			self.loading_country_chunks = 0 ;
			for (i=0,j=qs.length; i<j; i+=chunk) {
				self.loading_country_chunks++ ;
				var tmp = qs.slice(i,i+chunk);
				self.addCountries ( tmp ) ;
			}
		} ) ;
	} ,

	showCountries : function () {
		var self = this ;
		var h = '' ;
		var keys = [] ;
		$.each ( self.countries , function ( name , k ) { keys.push ( name ) } ) ;
		keys = keys.sort() ;
		$.each ( keys , function ( dummy , name ) {
			h += "<option value='" + self.countries[name] + "'>" + name + "</option>" ;
		} ) ;
		$('#country').html ( h ) ;
	} ,
	
	addCountries : function ( qs ) {
		var self = this ;
		$.getJSON ( self.api , {
			action : 'wbgetentities' ,
			ids : qs.join('|').toLowerCase() ,
			languages : 'en' ,
			format : 'json'
		} , function ( data ) {
			$.each ( data.entities , function ( k , v ) {
				var name = v.labels.en.value ;
				self.countries[name] = k ;
			} ) ;
			self.loading_country_chunks-- ;
			if ( self.loading_country_chunks > 0 ) return ;
			self.showCountries() ;
		} ) ;
	} ,

	isDisambiguation : function () {
		var self = this ;
		self.queue.push ( { mode:'set' , prop:'p107' , target_entity:'q4167410' } ) ;
		self.processed = 0 ;
		self.processNextQueueItem () ;
		return false ;
	} ,
	
	autoName : function () {
		var self = this ;
		
		var key = 'h1 input.wb-ui-propertyedittool-editablevalueinterface' ;
		var t = $($(key).get(0)) ;
		if ( t.val() != '' || t.tagName == 'span' ) return ; // Already has a title
		
		$.each ( ['en','de','fr','it','nl','sv','es'] , function ( k , v ) {
			var title = $($('td.wb-sitelinks-link-'+v + ' a').get(0)).text() ;
			if ( title == '' ) return ;
			title = title.replace ( /\s\(.+$/ , '' ) ;
			$($(key).get(0)).val(title).css({'background-color':'red'}) ;
			$($(key).get(0)).focus();
			
			return false ;
		} ) ;
	} ,
	
	processNextQueueItem : function () {
		var self = this ;
		if ( self.queue.length == 0 ) {
//			self.running = false ;
			if ( self.processed == 0 ) {
//				alert ( "No changes" ) ;
				return ;
			}
			// DONE
//			console.log ( "DONE" ) ;
//			location.reload();
			return ;
		}
		var q = self.queue.shift () ;
		if ( undefined === q.entity ) q.entity = self.q ;
		if ( q.mode == 'set' ) {
			var val = '{"entity-type":"item","numeric-id":' + q.target_entity.replace(/\D/g,'') + '}' ;
			self.tryCreateClaim ( q.entity , q.prop , val ) ;
		} else if ( q.mode == 'remove' ) {
			var val = '{"entity-type":"item","numeric-id":' + q.target_entity.replace(/\D/g,'') + '}' ;
			self.tryRemoveClaim ( q.entity , q.prop , val ) ;
		} else {
			console.log ( q ) ;
		}
	} ,

	tryRemoveClaim : function ( entity , property , value ) {
		var self = this ;
		entity = 'q' + entity.replace ( /\D/g , '' ) ;
		property = property.replace ( /\D/g , '' ) ;
		var value2 = JSON.parse ( value ) ;
		var nid = value2['numeric-id'] ;
		$.getJSON ( self.api , {
			action : 'wbgetentities' ,
			format : 'json' ,
			ids : entity ,
			props : 'info|claims'
		} , function ( data ) {
			if ( undefined !== data.entities[entity] ) {
				if ( undefined !== data.entities[entity].claims ) {
					if ( undefined !== data.entities[entity].claims['p'+property] ) {
						var n = data.entities[entity].claims['p'+property] ;
						var exists = false ;
						var id ;
						$.each ( n , function ( k , v ) {
							if ( v.mainsnak.datavalue.value['numeric-id'] == value.replace(/\D/g,'') ) {
								exists = true ;
								id = v.id ;
								return false ;
							}
						} ) ;
						if ( exists ) {
							self.removeClaim ( { revid:data.entities[entity].lastrevid , claim:id , entity:entity } ) ; // entity , property , value
//							console.log ( "p"+property+' exists for '+entity ) ;
							return ;
						}
					}
				}
			}
			console.log ( "Failed to remove " + entity + " / " + property + " : " + value ) ;
			self.processNextQueueItem() ;
		} ) ;
	} ,
		
	removeClaim : function ( o ) {
		var self = this ;
//		console.log ( "REMOVING" ) ;
//		console.log ( o ) ;
		$.post ( self.api , {
			action : 'query' ,
			prop : 'info' ,
			intoken : 'edit' ,
			titles : o.entity ,
			format : 'json'
		} , function ( data ) {
			var token , lastrevid ;
			$.each ( (data.query.pages||[]) , function ( k , v ) {
				token = v.edittoken ;
				lastrevid = v.lastrevid ;
			} ) ;
			
			if ( undefined === token ) {
				console.log ( "Cannot get edit token for " + entity ) ;
				self.processNextQueueItem() ;
				return ;
			}

			$.post ( self.api , {
				action : 'wbremoveclaims' ,
				claim : o.claim ,
				token : token ,
				baserevid : o.revid ,
				format : 'json',
				bot : true
			} , function ( data ) {
				var h = "<div style='color:red'>Removed " + JSON.stringify ( o ) + "</div>" ;
				$($('div.wb-claims').get(0)).append ( h ) ;

				self.processed++ ;
				self.processNextQueueItem() ;
			} , 'json' ) ;
			
			
			
		} , 'json' ) ;
	} ,

	tryCreateClaim : function ( entity , property , value ) {
		var self = this ;
		entity = 'q' + entity.replace ( /\D/g , '' ) ;
		property = property.replace ( /\D/g , '' ) ;
		var value2 = JSON.parse ( value ) ;
		var nid = value2['numeric-id'] ;
		$.getJSON ( self.api , {
			action : 'wbgetentities' ,
			format : 'json' ,
			ids : entity ,
			props : 'info|claims'
		} , function ( data ) {
			if ( undefined !== data.entities[entity] ) {
				if ( undefined !== data.entities[entity].claims ) {
					if ( undefined !== data.entities[entity].claims['p'+property] ) {
						var n = data.entities[entity].claims['p'+property] ;
						var exists = false ;
						$.each ( n , function ( k , v ) {
							if ( v.mainsnak.datavalue.value['numeric-id'] == nid ) {
								exists = true ;
								return false ;
							}
						} ) ;
						if ( exists ) {
							console.log ( "p"+property+' exists for '+entity ) ;
							self.processNextQueueItem() ;
							return ;
						}
					}
				}
			}
			self.createClaim ( entity , property , value ) ;
		} ) ;
	} ,
		
		
	createClaim : function ( entity , property , value ) {
//		console.log ( "Creating " + entity + " / " + property + " / " + value ) ;
		var self = this ;
		$.post ( self.api , {
			action : 'query' ,
			prop : 'info' ,
			intoken : 'edit' ,
			titles : entity ,
			format : 'json'
		} , function ( data ) {
			var token , lastrevid ;
			$.each ( (data.query.pages||[]) , function ( k , v ) {
				token = v.edittoken ;
				lastrevid = v.lastrevid ;
			} ) ;
			
			if ( undefined === token ) {
				console.log ( "Cannot get edit token for " + entity ) ;
				self.processNextQueueItem() ;
				return ;
			}
			
			property = property.replace(/\D/g,'') ;
			entity = entity.replace(/\D/g,'') ;
			var vo = JSON.parse ( value ) ;
			var value_id = vo['numeric-id']+'' ;
			
			var other_entity = ( entity.replace(/\D/g,'') != self.q.replace(/\D/g,'') ) ;
			
			$.post ( self.api , {
				action : 'wbcreateclaim' ,
				entity : 'q'+entity ,
				snaktype : 'value' ,
				property : 'p'+property ,
				value : value ,
				token : token ,
				baserevid : lastrevid ,
				format : 'json',
				bot : true
			} , function ( data ) {
				var id = 'added_' + self.id_cnt ;
				var h = "<div id='" + id + "'>" ;
				h += "Added " ;
				h += "<span class='added_entity_p'>" + property + "</span>" ;
				h += " &Rarr; " ;
				h += "<span class='added_entity_q'>" + value_id + "</span>" ;
				if ( other_entity ) h += " to entity <span class='added_entity_x'>" + entity + "</span>" ;
				h += ".</div>" ;
				$($('div.wb-claims').get(0)).append ( h ) ;
				self.updateEntity ( id , property , 'p' ) ;
				self.updateEntity ( id , value_id , 'q' ) ;
				if ( other_entity ) self.updateEntity ( id , entity.replace(/\D/g,'') , 'x' ) ;
				self.id_cnt++ ;
				
				self.processed++ ;
				self.processNextQueueItem() ;
			} , 'json' ) ;
			
			
			
		} , 'json' ) ;
	
	} ,
	
	updateEntity : function ( id , value , prefix ) {
		var self = this ;
		var q = prefix+value ;
		if ( prefix == 'x' ) q = 'q' + value ;
		$.getJSON ( self.api , {
			action : 'wbgetentities' ,
			ids : q ,
			format : 'json'
		} , function ( data ) {
			var labels = data.entities[q].labels ;
			var title = q ;
			if ( undefined !== labels ) {
				$.each ( ['en','de','fr'] , function ( k , v ) {
					if ( undefined === labels[v] ) return ;
					title = labels[v].value ;
					return false ;
				} ) ;
			}
			var h = "<a href='/wiki/" + q + "'>" + title + "</a>" ;
			$('#'+id+' span.added_entity_'+prefix).html ( h ) ;
		} ) ;
	} ,

	the_end : ''
} ;

$ ( function() {
	if ( mw.config.get('wgNamespaceNumber') != 0 ) return ;
	if ( mw.config.get('wgAction') != 'view' ) return ;
	
	wd_useful.init () ;
});