MediaWiki:Gadget-TranslationAdder-Data.js

Note: You may have to bypass your browser’s cache to see the changes. In addition, after saving a sitewide CSS file such as MediaWiki:Common.css, it will take 5-10 minutes before the changes take effect, even if you clear your cache.

  • Mozilla / Firefox / Safari: hold Shift while clicking Reload, or press either Ctrl-F5 or Ctrl-R (Command-R on a Macintosh);
  • Konqueror and Chrome: click Reload or press F5;
  • Opera: clear the cache in Tools → Preferences;
  • Internet Explorer: hold Ctrl while clicking Refresh, or press Ctrl-F5.

// {{documentation}}
// <nowiki>
// implicit dependencies : ext.gadget.LanguageUtils
/* jshint maxerr:1048576, strict:true, undef:true, latedef:true, es5:true */
/* global $, ScriptUtils, mw */

window.LangMetadata = function() {
	//Singleton
	if (arguments.callee.instance)
		return arguments.callee.instance;
	else
		arguments.callee.instance = this;

	// {{{ Metadata dictionaries
	// FIXME: Is it possible to query this information directly from [[Module:languages]]?
	var metadata = {
		aa: {
			haswikt: 1,
			sc: ["Latn", "Ethi"]
		},
		ab: {
			haswikt: 1,
			sc: ["Cyrl", "Latn", "Geor"]
		},
		aer: {
			sc: "Latn"
		},
		af: {
			g: ["s", "p"],
			haswikt: 1
		},
		ak: {
			haswikt: 1
		},
		akk: {
			g: ["m", "f", "m-p", "f-p"],
			sc: "Xsux"
		},
		als: {
			haswikt: 1
		},
		am: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1,
			sc: "Ethi"
		},
		an: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		ang: {
			alt: 1,
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			haswikt: 1
		},
		ar: {
			g: ["m", "f", "m-p", "f-p", "p"],
			alt: 1,
			haswikt: 1,
			sc: "Arab"
		},
		arc: {
			g: ["m", "f", "m-p", "f-p"],
			sc: ["Hebr", "Syrc"]
		},
		are: {},
		arz: {
			alt: 1,
			g: ["m", "f", "m-p", "f-p"],
			sc: "Arab"
		},
		as: {
			haswikt: 1,
			sc: "Beng"
		},
		ast: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		av: {
			haswikt: 1
		},
		ay: {
			haswikt: 1
		},
		az: {
			g: ["s", "p"],
			haswikt: 1,
			sc: ["Latn", "Cyrl", "Arab"]
		},
		ba: {
			g: ["s", "p"],
			sc: "Cyrl"
		},
		bar: {},
		"bat-smg": {
			g: ["m", "f", "m-p", "f-p"]
		},
		bbl: {
			sc: "Geor"
		},
		be: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1,
			sc: "Cyrl"
		},
		"be-x-old": {
			sc: "Cyrl"
		},
		bg: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1,
			sc: "Cyrl"
		},
		bh: {
			haswikt: 1,
			sc: "Deva"
		},
		bhb: {
			sc: "Deva"
		},
		bi: {
			haswikt: 1
		},
		blt: {
			sc: "Tavt"
		},
		bm: {
			haswikt: 1,
			sc: ["Latn", "Nkoo", "Arab"]
		},
		bn: {
			haswikt: 1,
			sc: "Beng"
		},
		bo: {
			haswikt: 1,
			sc: "Tibt"
		},
		br: {
			g: ["m", "f"],
			haswikt: 1
		},
		ca: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		cdo: {
			sc: "Hani"
		},
		ce: {
			sc: "Cyrl"
		},
		ch: {
			haswikt: 1
		},
		chr: {
			haswikt: 1,
			sc: "Cher"
		},
		cjy: {
			sc: "Hani"
		},
		ckb: {
			wiktprefix: "ku",
			sc: "Arab",
			wsc: "ku-Arab"
		},
		cmn: {
			sc: "Hani",
			wiktprefix: "zh"
		},
		co: {
			haswikt: 1
		},
		cpx: {
			sc: "Hani"
		},
		cr: {
			haswikt: 1,
			sc: "Cans"
		},
		crh: {},
		cs: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1
		},
		csb: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1
		},
		cu: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			sc: ["Cyrs", "Glag"]
		},
		cv: {
			sc: "Cyrl"
		},
		cy: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		czh: {
			sc: "Hani"
		},
		czo: {
			sc: "Hani"
		},
		da: {
			g: ["c", "n", "c-p", "n-p", "p"],
			haswikt: 1
		},
		dax: {},
		de: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p"],
			haswikt: 1,
			allowCaps: 1
		},
		dhg: {},
		djb: {},
		dji: {},
		djr: {},
		dng: {
			sc: "Cyrl"
		},
		dsb: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"]
		},
		dsx: {},
		duj: {},
		dv: {
			g: ["s", "p"],
			haswikt: 1,
			sc: "Thaa"
		},
		dz: {
			haswikt: 1,
			sc: "Tibt"
		},
		el: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			haswikt: 1
		},
		en: {
			g: ["s", "p"],
			haswikt: 1
		},
		eo: {
			g: ["s", "p"],
			haswikt: 1
		},
		es: {
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1
		},
		et: {
			g: ["s", "p"],
			haswikt: 1
		},
		ett: {
			g: ["s", "p"],
			sc: "Ital"
		},
		eu: {
			g: ["s", "p"],
			haswikt: 1
		},
		fa: {
			haswikt: 1,
			g: ["s", "p"],
			sc: "Arab",
			wsc: "fa-Arab"
		},
		// modelling on cmn, nb, prs
		"fa-cls": {
			wiktprefix: "fa",
			sc: "Arab",
			wsc: "fa-Arab"
		},
		// modelling on cmn, nb, prs
		"fa-ira": {
			wiktprefix: "fa",
			sc: "Arab",
			wsc: "fa-Arab"
		},		
		fi: {
			g: ["s", "p"],
			haswikt: 1
		},
		fil: {},
		fj: {
			haswikt: 1
		},
		fo: {
			g: ["m", "f", "n"],
			haswikt: 1
		},
		fr: {
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1
		},
		frm: {
			g: ["m", "f", "m-p", "f-p"]
		},
		fro: {
			g: ["m", "f", "m-p", "f-p"]
		},
		fur: {
			g: ["m", "f", "m-p", "f-p"],
		},
		fy: {
			g: ["c", "n", "p"],
			haswikt: 1
		},
		ga: {
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1
		},
		gan: {
			sc: "Hani"
		},
		gd: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		gez: {
			sc: "Ethi"
		},
		gl: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		"gmw-ecg": {
			g: ["m", "f", "n", "p"],
			allowCaps: 1
		},
		gmy: {
			sc: "Linb"
		},
		gn: {
			haswikt: 1
		},
		gnn: {
			sc: "Latn"
		},
		got: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			sc: "Goth"
		},
		grc: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p"]
		},
		gsw: {
			g: ["m", "f", "n", "p"],
			allowCaps: 1
		},
		gu: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			haswikt: 1,
			sc: "Gujr"
		},
		guf: {
			sc: "Latn"
		},
		gv: {
			haswikt: 1
		},
		ha: {
			haswikt: 1
		},
		hak: {
			sc: "Hani"
		},
		har: {
			sc: "Ethi"
		},
		he: {
			alt: 1,
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1,
			sc: "Hebr"
		},
		hi: {
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1,
			sc: "Deva"
		},
		hif: {
			sc: ["Latn", "Deva"]
		},
		hit: {
			sc: "Xsux"
		},
		hrx: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			haswikt: 1
		},
		hsb: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1
		},
		hsn: {
			sc: "Hani"
		},
		hu: {
			g: ["s", "p"],
			haswikt: 1
		},
		hy: {
			g: ["s", "p"],
			haswikt: 1,
			sc: "Armn"
		},
		ia: {
			haswikt: 1
		},
		id: {
			haswikt: 1
		},
		ie: {
			haswikt: 1
		},
		ik: {
			haswikt: 1
		},
		ike: {
			sc: "Cans"
		},
		ikt: {
			sc: "Cans"
		},
		io: {
			haswikt: 1
		},
		is: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			haswikt: 1
		},
		it: {
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1
		},
		iu: {
			haswikt: 1,
			sc: "Cans"
		},
		ja: {
			haswikt: 1,
			sc: "Jpan"
		},
		jay: {
			sc: "Latn"
		},
		jbo: {
			haswikt: 1
		},
		jv: {
			haswikt: 1
		},
		ka: {
			g: ["s", "p"],
			haswikt: 1
		}, // script should include "Geok" for Asomtavruli & Nuskhuri but prevents automatic transliteration?
		khb: {
			sc: ["Talu", "Lana", "Thai"]
		},
		kjh: {
			sc: "Cyrl"
		},
		kk: {
			haswikt: 1,
			g: ["s", "p"],
			sc: "Cyrl"
		},
		kkh: {
			sc: ["Lana", "Thai"]
		},
		kl: {
			haswikt: 1
		},
		km: {
			haswikt: 1,
			sc: "Khmr"
		},
		kn: {
			haswikt: 1,
			sc: "Knda"
		},
		kmr: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p"],
			wiktprefix: "ku"
		},
		ko: {
			haswikt: 1,
			sc: "Kore"
		},
		krc: {
			g: ["s", "p"],
			sc: "Cyrl"
		},
		ks: {
			haswikt: 1,
			sc: ["Arab", "Deva"],
			wsc: "ks-Arab"
		},
		kw: {
			haswikt: 1
		},
		ky: {
			haswikt: 1,
			g: ["s", "p"],
			sc: "Cyrl"
		},
		la: {
			alt: 1,
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			haswikt: 1
		},
		lb: {
			g: ["m", "f", "n", "p"],
			haswikt: 1,
			allowCaps: 1
		},
		lez: {
			sc: "Cyrl"
		},
		li: {
			haswikt: 1
		},
		lki: {
			wiktprefix: "ku"
		},
		lld: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		lmo: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},		
		ln: {
			haswikt: 1
		},
		lo: {
			haswikt: 1,
			sc: "Laoo"
		},
		lt: {
			alt: 1,
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		lv: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		lzz: {
			sc: "Geor"
		},
		mg: {
			haswikt: 1
		},
		mh: {
			haswikt: 1
		},
		mi: {
			g: 0,
			haswikt: 1
		},
		mk: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1,
			sc: "Cyrl"
		},
		ml: {
			haswikt: 1,
			sc: "Mlym"
		},
		mn: {
			g: ["s", "p"],
			haswikt: 1,
			sc: ["Cyrl", "Mong"]
		},
		mnp: {
			sc: "Hani"
		},
		mo: {
			haswikt: 1,
			sc: "Cyrl"
		},
		mol: {
			sc: "Cyrl"
		},
		mr: {
			g: ["m", "f", "n"],
			haswikt: 1,
			sc: "Deva"
		},
		ms: {
			haswikt: 1,
			sc: ["Latn", "Arab"]
		},
		mt: {
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1
		},
		mwp: {
			sc: "Latn"
		},
		my: {
			haswikt: 1,
			sc: "Mymr"
		},
		na: {
			haswikt: 1
		},
		nah: {
			haswikt: 1
		},
		nan: {
			wiktprefix: "zh-min-nan",
			sc: "Hani"
		},
		nb: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p"],
			wiktprefix: "no"
		},
		"nds-de": {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			wiktprefix: "nds"
		},
		"nds-nl": {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			wiktprefix: "nds"
		},
		ne: {
			haswikt: 1,
			sc: "Deva"
		},
		nl: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p"],
			haswikt: 1
		},
		nn: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p"],
			haswikt: 1
		},
		no: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p"],
			haswikt: 1
		},
		nod: {
			sc: "Lana"
		},
		non: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"]
		},
		oc: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		om: {
			haswikt: 1
		},
		or: {
			haswikt: 1,
			sc: "Orya"
		},
		orv: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			sc: "Cyrs"
		},
		osc: {
			sc: "Ital"
		},
		ota: {
			g: ["s", "p"],
			sc: "Arab",
			wsc: "ota-Arab"
		},
		pa: {
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1,
			sc: ["Guru", "Arab"]
		},
		pdt: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			wiktprefix: "nds"
		},
		peo: {
			sc: "Xpeo"
		},
		phn: {
			sc: "Phnx"
		},
		pi: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			haswikt: 1
		},
		pjt: {
			sc: "Latn"
		},
		pl: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1
		},
		pms: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		pox: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "impf", "pf"]
		},
		prs: {
			wiktprefix: "fa",
			sc: "Arab",
			wsc: "fa-Arab"
		},
		ps: {
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1,
			sc: "Arab",
			wsc: "ps-Arab"
		},
		pt: {
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1
		},
		qu: {
			haswikt: 1
		},
		rgn: {
			g: ["m", "f", "m-p", "f-p"],
		},		
		rit: {
			sc: "Latn"
		},
		rm: {
			g: ["m", "f"],
			haswikt: 1
		},
		rn: {
			haswikt: 1
		},
		ro: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p"],
			haswikt: 1,
			sc: ["Latn", "Cyrl"]
		},
		"roa-rup": {
			haswikt: 1
		},
		ru: {
			alt: 1,
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1,
			sc: "Cyrl"
		},
		rue: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			sc: "Cyrl"
		},
		ruo: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"]
		},
		rup: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			wiktprefix: "roa-rup"
		},
		ruq: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"]
		},
		rw: {
			haswikt: 1
		},
		sa: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"],
			haswikt: 1,
			sc: "Deva"
		},
		sah: {
			sc: "Cyrl"
		},
		sc: {
			haswikt: 1
		},
		scn: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		sco: {
			sc: "Latn"
		},
		sd: {
			haswikt: 1,
			sc: "Arab",
			wsc: "sd-Arab"
		},
		sdh: {
			wiktprefix: "ku"
		},
		sg: {
			haswikt: 1
		},
		sh: {
			alt: 1,
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1,
			sc: ["Latn", "Cyrl"]
		},
		si: {
			haswikt: 1,
			sc: "Sinh"
		},
		simple: {
			haswikt: 1
		},
		sk: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1
		},
		sl: {
			alt: 1,
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1
		},
		sm: {
			haswikt: 1
		},
		sn: {
			haswikt: 1
		},
		so: {
			haswikt: 1
		},
		spx: {
			sc: "Ital"
		},
		sq: {
			g: ["m", "f"],
			haswikt: 1
		},
		ss: {
			haswikt: 1
		},
		st: {
			haswikt: 1
		},
		su: {
			haswikt: 1
		},
		sux: {
			sc: "Xsux"
		},
		sv: {
			g: ["c", "n", "c-p", "n-p"],
			haswikt: 1
		},
		sva: {
			sc: "Geor"
		},
		sw: {
			nclass: 1,
			haswikt: 1
		},
		syc: {
			sc: "Syrc"
		},
		syr: {
			sc: "Syrc"
		},
		szl: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"]
		},
		ta: {
			haswikt: 1,
			sc: "Taml"
		},
		tdd: {
			sc: "Tale"
		},
		te: {
			haswikt: 1,
			sc: "Telu"
		},
		tg: {
			g: ["s", "p"],
			haswikt: 1,
			sc: "Cyrl"
		},
		th: {
			haswikt: 1,
			sc: "Thai"
		},
		ti: {
			haswikt: 1,
			sc: "Ethi"
		},
		tig: {
			sc: "Ethi"
		},
		tiw: {
			sc: "Latn"
		},
		tk: {
			g: ["s", "p"],
			haswikt: 1
		},
		tl: {
			haswikt: 1,
			sc: ["Latn", "Tglg"]
		},
		tmr: {
			sc: "Hebr"
		},
		tn: {
			haswikt: 1
		},
		to: {
			haswikt: 1
		},
		tpi: {
			haswikt: 1
		},
		tr: {
			g: ["s", "p"],
			alt: 1,
			haswikt: 1
		},
		ts: {
			haswikt: 1
		},
		tt: {
			g: ["s", "p"],
			haswikt: 1
		},
		tts: {
			sc: "Thai"
		},
		tw: {
			haswikt: 1
		},
		udi: {
			sc: ["Cyrl", "Latn", "Armn", "Geor"]
		},
		ug: {
			g: ["s", "p"],
			haswikt: 1,
			sc: "Arab",
			wsc: "ug-Arab"
		},
		uga: {
			sc: "Ugar"
		},
		uk: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p", "impf", "pf"],
			haswikt: 1,
			sc: "Cyrl"
		},
		ulk: {
			sc: "Latn"
		},
		ur: {
			g: ["m", "f", "m-p", "f-p", "p"],
			haswikt: 1,
			sc: "Arab",
			wsc: "ur-Arab"
		},
		uz: {
			g: ["s", "p"],
			haswikt: 1
		},
		vec: {
			g: ["m", "f", "m-p", "f-p"],
			haswikt: 1
		},
		vi: {
			haswikt: 1
		},
		vls: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p"]
		},
		vo: {
			haswikt: 1
		},
		wa: {
			haswikt: 1
		},
		wbp: {
			sc: "Latn"
		},
		wo: {
			haswikt: 1
		},
		wuu: {
			sc: "Hani"
		},
		xae: {
			sc: "Ital"
		},
		xcr: {
			sc: "Cari"
		},
		xfa: {
			sc: "Ital"
		},
		xh: {
			alt: 1,
			nclass: 1,
			haswikt: 1
		},
		xlc: {
			sc: "Lyci"
		},
		xld: {
			sc: "Lydi"
		},
		xlu: {
			sc: "Xsux"
		},
		xmf: {
			sc: "Geor"
		},
		xno: {
			g: ["m", "f", "m-p", "f-p"]
		},
		xrr: {
			sc: "Ital"
		},
		xst: {
			sc: "Ethi"
		},
		xum: {
			sc: "Ital"
		},
		xve: {
			sc: "Ital"
		},
		xvo: {
			sc: "Ital"
		},
		yi: {
			g: ["m", "f", "n", "m-p", "f-p", "n-p", "p"],
			haswikt: 1,
			sc: "Hebr"
		},
		yo: {
			haswikt: 1
		},
		yua: {
			g: ["s", "p"],
			alt: 1
		},
		yue: {
			sc: "Hani"
		},
		za: {
			haswikt: 1,
			sc: "Latn"
		},
		"zh-classical": {
			sc: "Hani"
		},
		"zh-min-nan": {
			haswikt: 1
		},
		"zh-yue": {
			sc: "Hani"
		},
		zu: {
			alt: 1,
			nclass: 1,
			haswikt: 1
		}
	};

	var clean = {
		aar: "aa",
		afar: "aa",
		abk: "ab",
		abkhazian: "ab",
		afr: "af",
		afrikaans: "af",
		aka: "ak",
		akan: "ak",
		amh: "am",
		amharic: "am",
		ara: "ar",
		arabic: "ar",
		arg: "an",
		aragonese: "an",
		asm: "as",
		assamese: "as",
		ava: "av",
		avaric: "av",
		ave: "ae",
		avestan: "ae",
		aym: "ay",
		aymara: "ay",
		aze: "az",
		azerbaijani: "az",
		bak: "ba",
		bashkir: "ba",
		bam: "bm",
		bambara: "bm",
		bel: "be",
		belarusian: "be",
		ben: "bn",
		bengali: "bn",
		bis: "bi",
		bislama: "bi",
		bod: "bo",
		tibetan: "bo",
		bs: "sh",
		bos: "sh",
		bosnian: "sh",
		bre: "br",
		breton: "br",
		bul: "bg",
		bulgarian: "bg",
		cat: "ca",
		catalan: "ca",
		ces: "cs",
		czech: "cs",
		cha: "ch",
		chamorro: "ch",
		che: "ce",
		chechen: "ce",
		chu: "cu",
		churchslavic: "cu",
		chv: "cv",
		chuvash: "cv",
		cor: "kw",
		cornish: "kw",
		cos: "co",
		corsican: "co",
		cre: "cr",
		cree: "cr",
		cym: "cy",
		welsh: "cy",
		dan: "da",
		danish: "da",
		deu: "de",
		german: "de",
		div: "dv",
		dhivehi: "dv",
		dzo: "dz",
		dzongkha: "dz",
		ekk: "et",
		ell: "el",
		greek: "el",
		eng: "en",
		english: "en",
		epo: "eo",
		esperanto: "eo",
		est: "et",
		estonian: "et",
		eus: "eu",
		basque: "eu",
		ewe: "ee",
		fao: "fo",
		faroese: "fo",
		fas: "fa",
		//"fa-ira": "fa",
		//"fa-cls": "fa",
		//prs: "fa",
		persian: "fa",
		fij: "fj",
		fijian: "fj",
		fil: "tl",
		fin: "fi",
		finnish: "fi",
		fra: "fr",
		french: "fr",
		fry: "fy",
		westernfrisian: "fy",
		ful: "ff",
		fulah: "ff",
		gla: "gd",
		scottishgaelic: "gd",
		gle: "ga",
		irish: "ga",
		glg: "gl",
		galician: "gl",
		glv: "gv",
		manx: "gv",
		grn: "gn",
		guarani: "gn",
		guj: "gu",
		gujarati: "gu",
		hat: "ht",
		haitian: "ht",
		hau: "ha",
		hausa: "ha",
		heb: "he",
		hebrew: "he",
		her: "hz",
		herero: "hz",
		hin: "hi",
		hindi: "hi",
		hmo: "ho",
		hirimotu: "ho",
		hr: "sh",
		hrv: "sh",
		croatian: "sh",
		hun: "hu",
		hungarian: "hu",
		hye: "hy",
		armenian: "hy",
		ibo: "ig",
		igbo: "ig",
		ido: "io",
		iii: "ii",
		sichuanyi: "ii",
		iku: "iu",
		inuktitut: "iu",
		ile: "ie",
		interlingue: "ie",
		ina: "ia",
		interlingua: "ia",
		ind: "id",
		indonesian: "id",
		ipk: "ik",
		inupiaq: "ik",
		isl: "is",
		icelandic: "is",
		ita: "it",
		italian: "it",
		jav: "jv",
		javanese: "jv",
		jpn: "ja",
		japanese: "ja",
		kal: "kl",
		kalaallisut: "kl",
		kan: "kn",
		kannada: "kn",
		kas: "ks",
		kashmiri: "ks",
		kat: "ka",
		georgian: "ka",
		kau: "kr",
		kanuri: "kr",
		kaz: "kk",
		kazakh: "kk",
		khm: "km",
		centralkhmer: "km",
		kik: "ki",
		kikuyu: "ki",
		kin: "rw",
		kinyarwanda: "rw",
		kir: "ky",
		kirghiz: "ky",
		kom: "kv",
		komi: "kv",
		kon: "kg",
		kongo: "kg",
		kor: "ko",
		korean: "ko",
		ksh: "gmw-cfr",
		kua: "kj",
		kuanyama: "kj",
		kv: "kpv",
		lao: "lo",
		lat: "la",
		latin: "la",
		lav: "lv",
		latvian: "lv",
		lim: "li",
		limburgan: "li",
		lin: "ln",
		lingala: "ln",
		lit: "lt",
		lithuanian: "lt",
		ltz: "lb",
		luxembourgish: "lb",
		lub: "lu",
		lubakatanga: "lu",
		lug: "lg",
		ganda: "lg",
		mah: "mh",
		marshallese: "mh",
		mal: "ml",
		malayalam: "ml",
		mar: "mr",
		marathi: "mr",
		chm: "mhr",
		mari: "mhr",
		mkd: "mk",
		macedonian: "mk",
		mlg: "mg",
		malagasy: "mg",
		mlt: "mt",
		maltese: "mt",
		mon: "mn",
		mongolian: "mn",
		mri: "mi",
		maori: "mi",
		msa: "ms",
		malay: "ms",
		mya: "my",
		burmese: "my",
		nau: "na",
		nauru: "na",
		hokkien: "nan-hbl",
		hokkienese: "nan-hbl",
		fujian: "nan-hbl",
		fujianese: "nan-hbl",
		hainam: "nan-hnm",
		hainan: "nan-hnm",
		hainanese: "nan-hnm",
		leizhou: "nan-luh",
		"zhx-lui": "nan-luh",
		teochew: "nan-tws",
		teochewese: "nan-tws",
		"zhx-teo": "nan-tws",
		wep: "nds-de",
		westphalian: "nds-de",
		germanlowgerman: "nds-de",
		dutchlowsaxon: "nds-nl",
		act: "nds-nl",
		achterhoeks: "nds-nl",
		drt: "nds-nl",
		drents: "nds-nl",
		gos: "nds-nl",
		gronings: "nds-nl",
		sdz: "nds-nl",
		sallands: "nds-nl",
		stl: "nds-nl",
		stellingwerfs: "nds-nl",
		twd: "nds-nl",
		twents: "nds-nl",
		vel: "nds-nl",
		veluws: "nds-nl",
		nav: "nv",
		navajo: "nv",
		nbl: "nr",
		southndebele: "nr",
		nde: "nd",
		northndebele: "nd",
		ndo: "ng",
		ndonga: "ng",
		nep: "ne",
		nepali: "ne",
		nld: "nl",
		dutch: "nl",
		flemish: "nl",
		nno: "nn",
		norwegiannynorsk: "nn",
		nob: "nb",
		norwegianbokmal: "nb",
		nor: "no",
		norwegian: "no",
		nya: "ny",
		nyanja: "ny",
		oci: "oc",
		occitan: "oc",
		oji: "oj",
		ojibwa: "oj",
		ori: "or",
		oriya: "or",
		orm: "om",
		oromo: "om",
		oss: "os",
		ossetian: "os",
		pan: "pa",
		panjabi: "pa",
		pfl: "gmw-rfr",
		pli: "pi",
		pali: "pi",
		pol: "pl",
		polish: "pl",
		por: "pt",
		portuguese: "pt",
		pus: "ps",
		pushto: "ps",
		que: "qu",
		quechua: "qu",
		roh: "rm",
		romansh: "rm",
		ron: "ro",
		romanian: "ro",
		rn: "rw",
		run: "rw",
		rundi: "rw",
		rus: "ru",
		russian: "ru",
		sag: "sg",
		sango: "sg",
		san: "sa",
		sanskrit: "sa",
		sin: "si",
		sinhala: "si",
		slk: "sk",
		slovak: "sk",
		slv: "sl",
		slovenian: "sl",
		sme: "se",
		northernsami: "se",
		smo: "sm",
		samoan: "sm",
		sna: "sn",
		shona: "sn",
		snd: "sd",
		sindhi: "sd",
		som: "so",
		somali: "so",
		sot: "st",
		southernsotho: "st",
		spa: "es",
		spanish: "es",
		sqi: "sq",
		albanian: "sq",
		srd: "sc",
		sardinian: "sc",
		sr: "sh",
		srp: "sh",
		serbian: "sh",
		ssw: "ss",
		swati: "ss",
		sun: "su",
		sundanese: "su",
		swa: "sw",
		swahili: "sw",
		swe: "sv",
		swedish: "sv",
		tah: "ty",
		tahitian: "ty",
		tam: "ta",
		tamil: "ta",
		tat: "tt",
		tatar: "tt",
		tel: "te",
		telugu: "te",
		tgk: "tg",
		taishanese: "zhx-tai",
		tajik: "tg",
		tgl: "tl",
		tagalog: "tl",
		tha: "th",
		thai: "th",
		tir: "ti",
		tigrinya: "ti",
		ton: "to",
		tonga: "to",
		tsn: "tn",
		tswana: "tn",
		tso: "ts",
		tsonga: "ts",
		tuk: "tk",
		turkmen: "tk",
		tur: "tr",
		turkish: "tr",
		twi: "tw",
		uig: "ug",
		uighur: "ug",
		ukr: "uk",
		ukrainian: "uk",
		urd: "ur",
		urdu: "ur",
		uzb: "uz",
		uzbek: "uz",
		ven: "ve",
		venda: "ve",
		vie: "vi",
		vietnamese: "vi",
		westflemish: "vls",
		vol: "vo",
		volapuk: "vo",
		wln: "wa",
		walloon: "wa",
		wol: "wo",
		wolof: "wo",
		xho: "xh",
		xhosa: "xh",
		yid: "yi",
		yiddish: "yi",
		yor: "yo",
		yoruba: "yo",
		zbc: "lod",
		zbe: "lod",
		zbw: "lod",
		zha: "za",
		zhuang: "za",
		zh: "cmn",
		zho: "cmn",
		chinese: "cmn",
		zul: "zu",
		zulu: "zu",
	};
	// }}}

	// FIXME: merge into above
	var c = 'Chinese';
	var a = 'Arabic';
	var nesting = {
		aae: 'Albanian/Arbëresh',
		aat: 'Albanian/Arvanitika',
		als: 'Albanian/Tosk',
		aln: 'Albanian/Gheg',
		apj: 'Apache',
		apm: 'Apache',
		apw: 'Apache',
		//Bai
		bca: 'Bai/Central Bai',
		bfc: 'Bai/Northern Bai',
		bfs: 'Bai/Southern Bai',
		lay: 'Bai/Lama Bai',		
		//Eastern Cham (cjm) and Western Cham (cja) to be nested under Cham (atitarev)
		cjm: 'Cham/Eastern Cham',
		cja: 'Cham/Western Cham',		
		syr: 'Aramaic',
		syc: 'Aramaic',
		xcl: 'Armenian',
		axm: 'Armenian',
		// ang:'English',enm:'English', don't nest English (Encyclopetey)
		//Persian nesting
		prs: 'Persian/Dari',
		"fa-cls": 'Persian/Classical Persian',
		"fa-ira": 'Persian/Iranian Persian',
		fro: 'French',
		frm: 'French',
		oge: 'Georgian',
		gsw: 'German',
		ksh: 'German',
		pfl: 'German',
		//gmh:'German',goh:'German', don't nest OHG/MHG (-sche)
		grc: 'Greek/Ancient Greek',
		gmy: 'Greek/Mycenaean Greek', //el:'Greek/Modern', don't nest Modern Greek (Atelaes)
		sga: 'Irish',
		mga: 'Irish',
		kmr: 'Kurdish/Northern Kurdish',
		ckb: 'Kurdish/Central Kurdish',
		sdh: 'Kurdish/Southern Kurdish',
		lki: 'Kurdish/Laki Kurdish',		
		//Lawa
		lwl: 'Lawa/Eastern Lawa',
		lcp: 'Lawa/Western Lawa',		
		"nds-de": 'Low German',
		"nds-nl": 'Low German',
		nb: 'Norwegian/Bokmål',
		nn: 'Norwegian/Nynorsk',
		mhr: 'Mari/Eastern Mari',
		mrj: 'Mari/Western Mari',
		cmg: 'Mongolian',
		cst: 'Ohlone/Northern Ohlone',
		css: 'Ohlone/Southern Ohlone',
		//Roglai
		rog: 'Roglai/Northern Roglai',
		rgs: 'Roglai/Southern Roglai',
        roc: 'Roglai/Cacgia Roglai',
		rmn: 'Romani',
		rml: 'Romani',
		rmc: 'Romani',
		rmf: 'Romani',
		rmo: 'Romani',
		rmy: 'Romani',
		rmw: 'Romani',
		dsb: 'Sorbian',
		hsb: 'Sorbian',
		osp: 'Spanish',
		//Sama
		ssb: 'Sama/Southern Sama',
		sml: 'Sama/Central Sama',
		sse: 'Sama/Balangingi Sama',
		slm: 'Sama/Pangutaran Sama',
		//Sami
		sma: 'Sami/Southern Sami',
		sju: 'Sami/Ume Sami',
		sje: 'Sami/Pite Sami',
		smj: 'Sami/Lule Sami',
		sme: 'Sami/Northern Sami',
		sjk: 'Sami/Kemi Sami',
		smn: 'Sami/Inari Sami',
		sms: 'Sami/Skolt Sami',
		sia: 'Sami/Akkala Sami',
		sjd: 'Sami/Kildin Sami',
		sjt: 'Sami/Ter Sami',	
		tji: 'Tujia/Northern Tujia',
		tjs: 'Tujia/Southern Tujia',
		owl: 'Welsh',
		wlm: 'Welsh',
		"yok-bvy": 'Yokuts',
		"yok-dly": 'Yokuts',
		"yok-gsy": 'Yokuts',
		"yok-kry": 'Yokuts',
		"yok-nvy": 'Yokuts',
		"yok-ply": 'Yokuts',
		"yok-svy": 'Yokuts',
		"yok-tky": 'Yokuts',
		zh: c,
		yue: c,
		dng: c,
		gan: c,
		hak: c,
		czh: c,
		cjy: c,
		cmn: c,
		mnp: c,
		cdo: c,
		nan: c,
		czo: c,
		cpx: c,
		wuu: c,
		hsn: c,
		lzh: c,
		cnp: c,
		csp: c,
		ltc: c,
		och: c,
		wxa: c,
		"nan-hbl": c,
		"nan-hnm": c,
		"nan-luh": c,
		"nan-tws": c,
		"zhx-sht": c,
		"zhx-sic": c,
		"zhx-tai": c,
		arq: a,
		aao: a,
		bbz: a,
		abv: a,
		shu: a,
		acy: a,
		adf: a,
		avl: a,
		arz: a,
		afb: a,
		ayh: a,
		acw: a,
		ayl: a,
		acm: a,
		ary: a,
		ars: a,
		apc: a,
		ayp: a,
		acx: a,
		aec: a,
		ayn: a,
		ssh: a,
		ajp: a,
		arb: a,
		apd: a,
		pga: a,
		acq: a,
		abh: a,
		aeb: a,
		auz: a
	};

	var stripArabicDiacritics = { strip: "\u064B\u064C\u064D\u064E\u064F\u0650\u0651\u0652" };
	var stripGraveAndAcute = { strip: "\u0300\u0301" };
	var fullToHalfWidthNumbers = {
		from: "0123456789",
		to: "0123456789"
	};
	// These should reflect the replacements made in [[Module:languages]], but should not necessarily be equal.
	var diacriticStrippers = {
		ang: {
			from: "ĀāǢǣĊċĒēĠġĪīŌōŪūȲȳ",
			to: "AaÆæCcEeGgIiOoUuYy",
			strip: "\u0304\u0307",
		}, //macron and above dot
		ar: stripArabicDiacritics,
		aao: stripArabicDiacritics,
		acm: stripArabicDiacritics,
		acx: stripArabicDiacritics,
		adf: stripArabicDiacritics,
		aeb: stripArabicDiacritics,
		afb: stripArabicDiacritics,
		ajp: stripArabicDiacritics,
		apc: stripArabicDiacritics,
		apd: stripArabicDiacritics,
		arq: stripArabicDiacritics,
		ary: stripArabicDiacritics,
		arz: stripArabicDiacritics,
		fa: stripArabicDiacritics,
		ps: stripArabicDiacritics,
		sd: stripArabicDiacritics,
		ur: stripArabicDiacritics,
		chl: {
			from: "ÁáÉéÍíÓóÚú",
			to: "AaEeIiOoUu",
			strip: "\u0304",
		}, //acute accent
		he: {
			strip: "\u05B0\u05B1\u05B2\u05B3\u05B4\u05B5\u05B6\u05B7\u05B8\u05B9\u05BA\u05BB\u05BC\u05BD\u05BF\u05C1\u05C2",
			from: "-'\"",
			to: "־׳״",
		},
		la: {
			from: "ĀāĒēĪīŌōŪūȲȳ",
			to: "AaEeIiOoUuYy",
			strip: "\u0304",
		}, //macron
		lt: {
			from: "áãàéẽèìýỹñóõòúù",
			to: "aaaeeeiyynooouu",
			strip: "\u0340\u0301\u0303",
		},
		nci: {
			from: "ĀāĒēĪīŌōŪūȲȳ",
			to: "AaEeIiOoUu",
			strip: "\u0304",
		}, //macron
		//strip ́ and ̀ on Cyrillic Slavic languages, Serbo-Croatian has a longer list
		ru: stripGraveAndAcute,
		uk: stripGraveAndAcute,
		be: stripGraveAndAcute,
		bg: stripGraveAndAcute,
		orv: stripGraveAndAcute,
		cu: stripGraveAndAcute,
		rue: stripGraveAndAcute,
		mk: stripGraveAndAcute,
		sh: {
			from: "ȀȁÀàȂȃÁáĀāȄȅÈèȆȇÉéĒēȈȉÌìȊȋÍíĪīȌȍÒòȎȏÓóŌōȐȑȒȓŔŕȔȕÙùȖȗÚúŪūѝӣ",
			to: "AaAaAaAaAaEeEeEeEeEeIiIiIiIiIiOoOoOoOoOoRrRrRrUuUuUuUuUuии",
			strip: "\u030F\u0300\u0311\u0301\u0304",
		},
		sl: {
			from: "áÁàÀâÂȃȂȁȀéÉèÈêÊȇȆȅȄíÍìÌîÎȋȊȉȈóÓòÒôÔȏȎȍȌŕŔȓȒȑȐúÚùÙûÛȗȖȕȔệỆộỘẹẸọỌəł",
			to: "aAaAaAaAaAeEeEeEeEeEiIiIiIiIiIoOoOoOoOoOrRrRrRuUuUuUuUuUeEoOeEoOel",
			strip: "\u0301\u0300\u0302\u0311\u030f\u0323",
		},
		kk: stripGraveAndAcute,
		ky: stripGraveAndAcute,
		tg: stripGraveAndAcute,
		sa: {
			strip: "ः",
		},
		/** visarga **/
		bo: {
			strip: "།",
		},
		/** shad **/
		tr: {
			from: "ÂâÛû",
			to: "AaUu",
			strip: "\u0302",
		},
		ja: fullToHalfWidthNumbers,
		cmn: fullToHalfWidthNumbers,
		yue: fullToHalfWidthNumbers,
		nan: fullToHalfWidthNumbers,
		ko: fullToHalfWidthNumbers,
		zu: {
			strip_init_hyphen: true,
		}
	};
	
	function stringOrNull(val) {
		return typeof val == "string" ? val : null;
	}
	
	function makeMap(obj) {
		var from = stringOrNull(obj.from);
		var to = stringOrNull(obj.to);
		var strip = stringOrNull(obj.strip);
		var map = {};
		if (from && to) {
			for (var i = 0; i < from.length; i++) {
				map[from.charAt(i)] = to.charAt(i);
			}
		}
		if (strip) {
			for (var ii = 0; ii < strip.length; ii++) {
				map[strip.charAt(ii)] = "";
			}
		}
		return map;
	}
	
	/** letters and number 1 are used instead of palochka **/
	var palochkaCorrections = {
		from: "Il1",
		to: "ӏӏӏ"
	};
	
	// 
	var arabicYa = "ي"; // Arabic letter yāʾ (U+064A ARABIC LETTER YEH)
	var arabicKaf = "ك"; // Arabic letter kāf (U+0643 ARABIC LETTER KAF)
	var farsiYe = "ی"; // Persian letter ye (U+06CC ARABIC LETTER FARSI YEH)
	var farsiKaf = "ک"; // Persian letter kâf (U+06A9 ARABIC LETTER KEHEH)
	var alifMaqsura = "ى"; // Arabic letter ʾalif maqṣūra (U+0649 ARABIC LETTER ALEF MAKSURA)
	
	/** commonly misspelled Persian letters (Arabic instead of Persian) (to be expanded) **/
	var persianCorrections = {
		from: arabicKaf + arabicYa + alifMaqsura,
		to: farsiKaf + farsiYe + farsiYe,
	};
	
	// These replacements will be applied when a word is submitted.
	var orthographicalCorrections = {
		// Replace grave accents with acute accents for translations
		// into Bulgarian per Wiktionary policy
		bg: {
			map: { "\u0300": "\u0301", "Ѐ": "Е́", "Ѝ": "И́", "ѐ": "е́", "ѝ": "и́" },
		},
		abq: palochkaCorrections,
		ady: palochkaCorrections,
		av: palochkaCorrections,
		ce: palochkaCorrections,
		dar: palochkaCorrections,
		inh: palochkaCorrections,
		kbd: palochkaCorrections,
		lbe: palochkaCorrections,
		lez: palochkaCorrections,
		tab: palochkaCorrections,
		/** Roman to Cyrillic**/
		cv: {
			from: "ĂăĔĕÇçŸÿ",
			to: "ӐӑӖӗҪҫӲӳ",
		},
		kv: {
			from: "ÖöIi",
			to: "ӦӧІі",
		},
		koi: {
			from: "ÖöIi",
			to: "ӦӧІі",
		},
		kpv: {
			from: "ÖöIi",
			to: "ӦӧІі",
		},
		os: {
			from: "Ææ",
			to: "Ӕӕ",
		},
		/* Obsolete or incorrectly used letters */
		mn: {
			from: "ЄєѲѳЇїVv",
			to: "ӨөӨөҮүҮү",
			strip: "\u0300\u0301",
		},
		/* cedilla to comma below */
		ro: {
			from: "ŞŢşţ",
			to: "ȘȚșț",
		},
		/** ʻ is a standard symbol in Uzbek but is often replaced with ' or ` **/
		uz: {
			from: "'`",
			to: "ʻʻ",
		},
		fa: persianCorrections,
		"fa-ira": persianCorrections,
		"fa-cls": persianCorrections,
		prs: persianCorrections,
		ur: persianCorrections,
		/** commonly misspelled Arabic letters (Persian instead of Arabic) (to be expanded) **/
		ar: {
			from: farsiKaf + farsiYe,
			to: arabicKaf + arabicYa,
		},
		ota: {
			from: farsiKaf + arabicYa + alifMaqsura,
			to: arabicKaf + farsiYe + farsiYe,
		},
		ps: {
			from: arabicKaf,
			to: farsiKaf,
		},
		/** some letters are considered more standard (to be expanded) **/
		cu: {
			from: "ыѹ",
			to: "ꙑу",
		},
		/** some letters are considered more standard (to be expanded) **/
		orv: {
			from: "ыѹ",
			to: "ꙑу",
		},
		/** obsolete letters **/
		ab: {
			from: "ҔҕҦҧ",
			to: "ӶӷԤԥ",
		},
	};
	
	//Returns true if a Wiktionary exists for the specified language
	this.hasWiktionary = function(lang) {
		if (metadata[lang] && (metadata[lang].haswikt || metadata[lang].wiktprefix))
			return true;
	};
	//Returns the domain-name prefix of the Wiktionary for the specified language
	this.getWiktionaryPrefix = function(lang) {
		if (metadata[lang])
			return metadata[lang].wiktprefix || (metadata[lang].haswikt && lang);
	};
	
	// Keep this in sync with ignore_caps in [[Module:translations]].
	this.ignoreCaps = { "ko": true };
	
	// Calls the callback with a boolean indicating whether the specified language
	// has a Wiktionary with the specified entry. The callback might be called
	// synchronously, or it might be called asynchronously.
	this.hasWiktionaryWithEntry = function(lang, title, callback) {
		if (this.hasWiktionary(lang)) {
			if (this.ignoreCaps[lang])
				title = title.replace(/^\^/, "");
			
			// Use this when we want to give up support for Internet Explorer 11.
			// URL constructor and URLSearchParams are not supported in IE11.
			// var url = new URL("https://" + this.getWiktionaryPrefix(lang) + ".wiktionary.org/w/api.php");
			// url.search = new URLSearchParams({
			// 	"format": "json",
			// 	"formatversion": "2",
			// 	"action": "query",
			// 	"titles": title,
			// 	"converttitles": 1,
			// 	"origin": "*",
			// });
			
			var url = new mw.Uri("https://" + this.getWiktionaryPrefix(lang) + ".wiktionary.org/w/api.php");
			url.extend({
				"format": "json",
				"formatversion": "2",
				"action": "query",
				"titles": title,
				"converttitles": 1,
				"origin": "*",
			});
			
			$.ajax({
				type: 'GET',
				url: url.toString(),
				dataType: 'json',
				headers: { 'Api-User-Agent': 'EnWiktTranslationAdderGadget/0.0 (https://en.wiktionary.org/wiki/MediaWiki:Gadget-TranslationAdder.js)' },
			}).done(function(data)  {
				var page = data && data.query && data.query.pages && data.query.pages[0];
				callback(page instanceof Object ? !page.missing : false);
			});
			
		} else
			callback(false);
	};

	//Given a language code return a default script code.
	this.guessScript = function(lang) {
		var scripts = (new ScriptUtils()).GetScriptsByLangCode(lang);
		if (scripts && scripts.length > 0) return scripts[0];
		else return false;
		
		if (metadata[lang]) {
			// enwikt language template? (ur-Arab, polytonic)
			if (metadata[lang].wsc) {
				return metadata[lang].wsc;
			}
			// ISO script code? (Arab, Grek)
			if (metadata[lang].sc) {
				if (typeof metadata[lang].sc == 'object')
					return metadata[lang].sc[0];
				else
					return metadata[lang].sc;
			}
		}

		return false;
	};

	// In a given language, would we expect a translation of the title to have the capitalisation
	// of word?
	this.expectedCase = function(lang, title, word) {
		if (metadata[lang] && metadata[lang].allowCaps)
			return true;

		if (title.substr(0, 1).toLowerCase() != title.substr(0, 1))
			return true;

		return word.substr(0, 1).toLowerCase() == word.substr(0, 1);
	};

	//Returns a string of standard gender letters (mfnc) or an empty string
	this.getGenders = function(lang) {
		if (metadata[lang])
			return metadata[lang].g;
	};

	//Returns a string of standard noun class numbers or an empty string
	this.hasNounClasses = function(lang) {
		if (metadata[lang])
			return metadata[lang].nclass;
	};

	//Returns true if the specified lang uses optional vowels or diacritics
	this.needsRawPageName = function(lang) {
		if (metadata[lang])
			return metadata[lang].alt && !diacriticStrippers[lang];
	};
	
	function applyMap(map, str) {
		var input = str.split("");
		var output = "";

		for (var i = 0; i < input.length; i++) {
			var char = input[i];
			var repl = map[char];
			output += repl ? repl : char;
		}
		return output;
	}
	
	this.applyOrthographicalCorrections = function(lang, word) {
		word = word.replace('\xAD', ''); // remove soft hyphens
		var corrections = orthographicalCorrections[lang];
		if (corrections) {
			var map = corrections.map ? corrections.map : makeMap(corrections);
			return applyMap(map, word);
		}
		return word;
	};

	// Computes the raw page name by removing diacritics (for Latin, etc.)
	this.computeRawPageName = function(lang, word) {
		var stripper = diacriticStrippers[lang];
		if (stripper) {
			var map = makeMap(stripper);
			var output = applyMap(map, word);

			if (stripper.strip_init_hyphen && output.length > 0 && output.charAt(0) == '-')
				output = output.substr(1);

			return output;
		}
	};

	// Calls [[Module:links]]'s 'remove_diacritics' method on word and rawPageName,
	// and invokes callback with two arguments: (1) the *real* raw page name
	// (superseding even rawPageName), and (2) whether this real raw page name
	// needs to be explicitly specified in the wikitext (i.e., whether the raw page
	// name computed from rawPageName is different from the one that would have been
	// computed from just word).
	this.retrieveRawPageName = function(lang, word, rawPageName, callback) {
		var ents = {
			'<': 'lt',
			'&': 'amp',
			'>': 'gt'
		};
		var temps = {
			'|': '!',
			'=': '=',
			'{': '(',
			'}': ')'
		};

		function encode(s) {
			s = s || '';
			s = s.replace(/[|={}]/g, function(c) {
				return '{{' + temps[c] + '}}';
			});
			s = s.replace(/[<&>]/g, function(c) {
				return '&' + ents[c] + ';';
			});
			s = s.replace(/\t/g, ' ');
			//s = encodeURIComponent(s);
			return s;
		}

		function removeDiacritics(s) {
			return '{{#invoke:languages/templates|getByCodeAllowEtym|' + lang + '|makeEntryName|' + encode(s) + '}}';
		}

		var text = removeDiacritics(word) + '\t' + removeDiacritics(rawPageName || word);
		$.ajax({
			dataType: "json",
			url: '/w/api.php',
			data: {
				format: 'json',
				action: 'expandtemplates',
				prop: 'wikitext',
				text: text
			},
			success: function(data) {
				data = data && data.expandtemplates && data.expandtemplates.wikitext;
				if (/<!--/.test(data)) {
					data = false;
				}
				if (data) {
					data = data && data.split('\t');
					var wordMinus = data[0];
					var rawPageNameMinus = data[1];
					callback(rawPageNameMinus || wordMinus, rawPageNameMinus != wordMinus);
				} else {
					callback(rawPageName || word, rawPageName && rawPageName != word);
				}
			}
		});
	};

	//Given user input, return a language code. Normalises ISO 639-1 codes and names to 639-3.
	this.cleanLangCode = function(lang) {
		var key = lang.toLowerCase().replace(' ', '');
		if (clean[key])
			return clean[key];
		else
			return lang;
	};

	// Get the nesting for a given sub-language
	this.getNested = function(lang) {
		if (nesting[lang])
			return nesting[lang];
		else
			return "";
	};

	function temporalSortKey(langname) {
		return langname.replace(/^(Ancient|Classical|Old|Middle|Early Modern|Modern) (.*)/, function(m, modifier, name) {
			return ({
				Ancient: 0,
				Old: 1,
				Middle: 2,
				"Early Modern": 3,
				Modern: 4
			})[modifier] + name;
		});
	}

	// For enforcing an ordering on nested languages.
	this.nestsBefore = function(a, b) {
		return temporalSortKey(a) < temporalSortKey(b);
	};

	this.getScripts = function(lang) {
		var scripts = (new window.ScriptUtils()).GetScriptsByLangCode(lang) || [];
		return scripts;
	};
};
//</nowiki>