1
0
mirror of https://github.com/gnosygnu/xowa.git synced 2026-03-02 03:49:30 +00:00

'v3.8.5.1'

This commit is contained in:
gnosygnu
2016-08-29 23:31:58 -04:00
parent e4a2af026b
commit 232838c732
292 changed files with 4502 additions and 1838 deletions

View File

@@ -64,7 +64,7 @@ public class Xot_defn_tmpl implements Xot_defn {
public boolean Tmpl_evaluate(Xop_ctx ctx, Xot_invk caller, Bry_bfr bfr) {
if (root == null) Parse_tmpl(ctx);
Xoae_page page = ctx.Page();
if (!page.Tmpl_stack_add(full_name)) {
if (!ctx.Wiki().Parser_mgr().Tmpl_stack_add(full_name)) {
bfr.Add_str_a7("<!-- template loop detected:" + gplx.langs.htmls.Gfh_utl.Escape_html_as_str(String_.new_u8(name)) + " -->");
Xoa_app_.Usr_dlg().Log_many("", "", "template loop detected: url=~{0} name=~{1}", ctx.Page().Url().To_str(), name);
return false;
@@ -87,7 +87,7 @@ public class Xot_defn_tmpl implements Xot_defn {
boolean result = root.Subs_get(i).Tmpl_evaluate(ctx, data_raw, caller, bfr);
if (!result) rv = false;
}
page.Tmpl_stack_del();
ctx.Wiki().Parser_mgr().Tmpl_stack_del();
return rv;
}
public Xot_defn Clone(int id, byte[] name) {throw Err_.new_unimplemented();}

View File

@@ -43,7 +43,7 @@ class Xot_fmtr_prm implements Xot_fmtr {
}
else // invk mode
self.Tmpl_evaluate(ctx, src, caller, trg);
} static final byte[] Bry_bgn = new byte[] {Byte_ascii.Curly_bgn, Byte_ascii.Curly_bgn, Byte_ascii.Curly_bgn}, Bry_end = new byte[] {Byte_ascii.Curly_end, Byte_ascii.Curly_end, Byte_ascii.Curly_end};
} private static final byte[] Bry_bgn = new byte[] {Byte_ascii.Curly_bgn, Byte_ascii.Curly_bgn, Byte_ascii.Curly_bgn}, Bry_end = new byte[] {Byte_ascii.Curly_end, Byte_ascii.Curly_end, Byte_ascii.Curly_end};
public void Reg_tmpl(Xop_ctx ctx, byte[] src, Xop_tkn_itm name_tkn, int args_len, Arg_nde_tkn[] args) {
trg.Add(Xop_curly_bgn_lxr.Hook);
++depth;

View File

@@ -17,12 +17,13 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package gplx.xowa.parsers.tmpls; import gplx.*; import gplx.xowa.*; import gplx.xowa.parsers.*;
import gplx.core.envs.*;
import gplx.xowa.langs.*; import gplx.xowa.langs.kwds.*; import gplx.xowa.langs.vnts.*; import gplx.xowa.langs.vnts.converts.*; import gplx.xowa.langs.funcs.*;
import gplx.xowa.wikis.nss.*;
import gplx.xowa.wikis.caches.*; import gplx.xowa.xtns.scribunto.*; import gplx.xowa.xtns.pfuncs.*; import gplx.xowa.xtns.pfuncs.ttls.*; import gplx.xowa.wikis.pages.*;
import gplx.xowa.wikis.data.tbls.*;
import gplx.xowa.parsers.miscs.*;
import gplx.xowa.langs.*; import gplx.xowa.langs.kwds.*; import gplx.xowa.langs.funcs.*;
import gplx.xowa.xtns.pfuncs.*; import gplx.xowa.xtns.pfuncs.ttls.*;
import gplx.xowa.wikis.pages.*; import gplx.xowa.wikis.nss.*; import gplx.xowa.wikis.caches.*; import gplx.xowa.wikis.data.tbls.*;
public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
public Xot_invk_tkn(int bgn, int end) {this.Tkn_ini_pos(false, bgn, end);}
@Override public byte Tkn_tid() {return typeId;} private byte typeId = Xop_tkn_itm_.Tid_tmpl_invk;
public void Tkn_tid_to_txt() {typeId = Xop_tkn_itm_.Tid_txt;}
public Arg_nde_tkn Name_tkn() {return name_tkn;} public Xot_invk_tkn Name_tkn_(Arg_nde_tkn v) {name_tkn = v; return this;} Arg_nde_tkn name_tkn = Arg_nde_tkn.Null;
public byte Defn_tid() {return defn_tid;} private byte defn_tid = Xot_defn_.Tid_null;
public int Tmpl_subst_bgn() {return tmpl_subst_bgn;} private int tmpl_subst_bgn;
@@ -49,23 +50,36 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
}
}
@Override public boolean Tmpl_evaluate(Xop_ctx ctx, byte[] src, Xot_invk caller, Bry_bfr bfr) { // this="{{t|{{{0}}}}}" caller="{{t|1}}"
// init common
boolean rv = false;
Xot_defn defn = tmpl_defn; Xowe_wiki wiki = ctx.Wiki(); Xol_lang_itm lang = wiki.Lang();
byte[] name_ary = defn.Name(), argx_ary = Bry_.Empty; Arg_itm_tkn name_key_tkn = name_tkn.Key_tkn();
Xowe_wiki wiki = ctx.Wiki();
Xol_lang_itm lang = wiki.Lang();
// init defn / name
Xot_defn defn = tmpl_defn;
byte[] name_ary = defn.Name();
byte[] name_ary_orig = Bry_.Empty;
int name_bgn = 0, name_ary_len = 0;
Arg_itm_tkn name_key_tkn = name_tkn.Key_tkn();
// init more
byte[] argx_ary = Bry_.Empty;
boolean subst_found = false;
boolean name_had_subst = false;
boolean template_prefix_found = false;
if (defn == Xot_defn_.Null) { // tmpl_name is not exact match; may be dynamic, subst, transclusion, etc..
if (name_key_tkn.Itm_static() == Bool_.N_byte) { // tmpl is dynamic; EX:{{{{{1}}}|a}}
// tmpl_name does not exist in db; may be dynamic, subst, transclusion, etc..
if (defn == Xot_defn_.Null) {
// dynamic tmpl; EX:{{{{{1}}}|a}}
if (name_key_tkn.Itm_static() == Bool_.N_byte) {
Bry_bfr name_tkn_bfr = Bry_bfr_.New_w_size(name_tkn.Src_end() - name_tkn.Src_bgn());
if (defn_tid == Xot_defn_.Tid_subst)
name_tkn_bfr.Add(Get_first_subst_itm(lang.Kwd_mgr()));
name_tkn.Tmpl_evaluate(ctx, src, caller, name_tkn_bfr);
name_ary = name_tkn_bfr.To_bry_and_clear();
}
else // tmpl is static; note that dat_ary is still valid but rest of name may not be; EX: {{subst:name{{{1}}}}}
// tmpl is static; note that dat_ary is still valid but rest of name may not be; EX: {{subst:name{{{1}}}}}
else
name_ary = Bry_.Mid(src, name_key_tkn.Dat_bgn(), name_key_tkn.Dat_end());
name_had_subst = name_key_tkn.Dat_ary_had_subst();
name_ary_orig = name_ary; // cache name_ary_orig
@@ -73,8 +87,9 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
name_bgn = Bry_find_.Find_fwd_while_not_ws(name_ary, 0, name_ary_len);
if ( name_ary_len == 0 // name is blank; can occur with failed inner tmpl; EX: {{ {{does not exist}} }}
|| name_bgn == name_ary_len // name is ws; EX: {{test| }} -> {{{{{1}}}}}is whitespace String; PAGE:en.d:wear_one's_heart_on_one's_sleeve; EX:{{t+|fr|avoir le cœur sur la main| }}
) {
bfr.Add(Ary_unknown_bgn).Add(Ary_dynamic_is_blank).Add(Ary_unknown_end); // FUTURE: excerpt actual String; WHEN: add raw to defn
) {
Gfo_usr_dlg_.Instance.Warn_many("", "", "parser.tmpl:dynamic is blank; page~{0}", ctx.Page().Url_bry_safe());
bfr.Add_str_a7("(? [[dynamic is blank]] ?)");
return false;
}
if (name_ary[name_bgn] == Byte_ascii.Colon) { // check 1st letter for transclusion
@@ -200,7 +215,7 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
else { // some templates produce null ttls; EX: "Citation needed{{subst"
defn = wiki.Cache_mgr().Defn_cache().Get_by_key(ttl.Page_db());
if (defn == null && ctx.Tmpl_load_enabled())
defn = Load_defn(wiki, ctx, this, ttl, name_ary);
defn = Xot_invk_tkn_.Load_defn(wiki, ctx, this, ttl, name_ary);
}
}
}
@@ -219,40 +234,35 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
}
defn = wiki.Cache_mgr().Defn_cache().Get_by_key(name_ary);
if (defn == null && ctx.Tmpl_load_enabled())
defn = Load_defn(wiki, ctx, this, ttl, name_ary);
defn = Xot_invk_tkn_.Load_defn(wiki, ctx, this, ttl, name_ary);
if (defn == null) defn = Xot_defn_.Null;
}
}
Xot_defn_trace trace = ctx.Defn_trace(); int trg_bgn = bfr.Len();
switch (defn.Defn_tid()) {
case Xot_defn_.Tid_null: // defn is unknown
if (ignore_hash == null) { // ignore SafeSubst templates
ignore_hash = Hash_adp_bry.ci_a7();
ignore_hash.Add_str_obj("Citation needed{{subst", String_.Empty);
ignore_hash.Add_str_obj("Clarify{{subst", String_.Empty);
}
if (ignore_hash.Get_by_bry(name_ary) == null) {
if (Pfunc_rel2abs.Rel2abs_ttl(name_ary, name_bgn, name_ary_len)) {// rel_path; EX: {{/../Peer page}}; DATE:2013-03-27
Bry_bfr tmp_bfr = ctx.Wiki().Utl__bfr_mkr().Get_b512();
name_ary = Pfunc_rel2abs.Rel2abs(tmp_bfr, Bry_.Mid(name_ary, name_bgn, name_ary_len), ctx.Page().Ttl().Raw());
name_ary = Pfunc_rel2abs.Rel2abs(tmp_bfr, wiki.Parser_mgr().Rel2abs_ary(), Bry_.Mid(name_ary, name_bgn, name_ary_len), ctx.Page().Ttl().Raw());
tmp_bfr.Mkr_rls();
return SubEval(ctx, wiki, bfr, name_ary, caller, src);
}
if (subst_found)
return Transclude(ctx, wiki, bfr, template_prefix_found, name_ary, caller, src);
Print_not_found__w_template(bfr, wiki.Ns_mgr(), name_ary);
Xot_invk_tkn_.Print_not_found__w_template(bfr, wiki.Ns_mgr(), name_ary);
return false;
}
break;
case Xot_defn_.Tid_func:
try {
Eval_func(ctx, src, caller, this, bfr, defn, argx_ary);
Xot_invk_tkn_.Eval_func(ctx, src, caller, this, bfr, defn, argx_ary);
rv = true;
} catch (Exception e) {
if (Env_.Mode_testing())
throw Err_.new_exc(e, "xo", "failed to evaluate function", "page", ctx.Page().Ttl().Full_txt_w_ttl_case(), "defn", defn.Name(), "src", String_.new_u8(src, this.Src_bgn(), this.Src_end()));
else {
wiki.Appe().Usr_dlg().Warn_many("", "", "failed to evaluate function: page=~{0} defn=~{1} src=~{2} err=~{3}", ctx.Page().Ttl().Full_txt_w_ttl_case(), defn.Name(), String_.new_u8(src, this.Src_bgn(), this.Src_end()), Err_.Message_gplx_log(e));
wiki.Appe().Usr_dlg().Warn_many("", "", "failed to evaluate function: page=~{0} defn=~{1} src=~{2} err=~{3}", ctx.Page().Ttl().Full_txt_w_ttl_case(), defn.Name(), Bry_.Replace_nl_w_tab(src, this.Src_bgn(), this.Src_end()), Err_.Message_gplx_log(e));
rv = false;
}
}
@@ -266,7 +276,7 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
Bry_bfr rslt_bfr = wiki.Utl__bfr_mkr().Get_k004();
try {
Bld_key(invk_tmpl, name_ary, rslt_bfr);
Xot_invk_tkn_.Bld_key(invk_tmpl, name_ary, rslt_bfr);
byte[] rslt_key = rslt_bfr.To_bry_and_clear();
Object o = wiki.Cache_mgr().Tmpl_result_cache().Get_by(rslt_key);
Xopg_tmpl_prepend_mgr prepend_mgr = ctx.Page().Tmpl_prepend_mgr().Bgn(bfr);
@@ -297,7 +307,7 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
break;
}
return rv;
} private static final byte[] Ary_unknown_bgn = Bry_.new_a7("(? [["), Ary_unknown_end = Bry_.new_a7("]] ?)"), Ary_dynamic_is_blank = Bry_.new_a7("dynamic is blank");
}
private boolean Popup_skip(Xop_ctx ctx, byte[] ttl, Bry_bfr bfr) {
boolean skip = false;
skip = this.Src_end() - this.Src_bgn() > ctx.Tmpl_tkn_max();
@@ -316,38 +326,6 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
else
return false;
}
public static void Eval_func(Xop_ctx ctx, byte[] src, Xot_invk caller, Xot_invk invk, Bry_bfr bfr, Xot_defn defn, byte[] argx_ary) {
Pf_func_base defn_func = (Pf_func_base)defn;
int defn_func_id = defn_func.Id();
defn_func = (Pf_func_base)defn_func.New(defn_func_id, defn_func.Name()); // NOTE: always make copy b/c argx_ary may be dynamic
if (argx_ary != Bry_.Empty) defn_func.Argx_dat_(argx_ary);
defn_func.Eval_argx(ctx, src, caller, invk);
if (defn_func_id == Xol_kwd_grp_.Id_invoke) // NOTE: if #invoke, set frame_ttl to argx, not name; EX:{{#invoke:A}}
invk.Frame_ttl_(Bry_.Add(Xow_ns_.Bry__module_w_colon, Xoa_ttl.Replace_unders(defn_func.Argx_dat()))); // NOTE: always prepend "Module:" to frame_ttl; DATE:2014-06-13; NOTE: always use spaces; DATE:2014-08-14; always use canonical English "Module"; DATE:2015-11-09
Bry_bfr bfr_func = Bry_bfr_.New();
defn_func.Func_evaluate(bfr_func, ctx, caller, invk, src);
if (caller.Rslt_is_redirect()) // do not prepend if page is redirect; EX:"#REDIRECT" x> "\n#REDIRECT" DATE:2014-07-11
caller.Rslt_is_redirect_(false); // reset flag; needed for TEST; kludgy, but Rslt_is_redirect is intended for single use
else
ctx.Page().Tmpl_prepend_mgr().End(ctx, bfr, bfr_func.Bfr(), bfr_func.Len(), Bool_.N);
bfr.Add_bfr_and_clear(bfr_func);
}
private static Hash_adp_bry ignore_hash;
public static boolean Cache_enabled = false;
private static void Bld_key(Xot_invk invk, byte[] name_ary, Bry_bfr bfr) {
bfr.Clear();
bfr.Add(name_ary);
int args_len = invk.Args_len();
for (int i = 0; i < args_len; i++) {
Arg_nde_tkn nde = invk.Args_get_by_idx(i);
bfr.Add_byte(Byte_ascii.Pipe);
if (nde.KeyTkn_exists()) {
bfr.Add(nde.Key_tkn().Dat_ary());
bfr.Add_byte(Byte_ascii.Eq);
}
bfr.Add(nde.Val_tkn().Dat_ary());
}
}
private boolean Transclude(Xop_ctx ctx, Xowe_wiki wiki, Bry_bfr bfr, boolean template_prefix_found, byte[] name_ary, Xot_invk caller, byte[] src) {
Xoa_ttl page_ttl = Xoa_ttl.Parse(wiki, name_ary); if (page_ttl == null) return false; // ttl not valid; EX: {{:[[abc]]}}
byte[] transclude_src = null;
@@ -369,7 +347,7 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
return Eval_sub(ctx, transclude_tmpl, caller, src, bfr);
}
else {
Print_not_found__by_transclude(bfr, wiki.Ns_mgr(), template_prefix_found, name_ary);
Xot_invk_tkn_.Print_not_found__by_transclude(bfr, wiki.Ns_mgr(), template_prefix_found, name_ary);
return false;
}
}
@@ -383,34 +361,6 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
doc.Add_bfr_and_clear(tmp_bfr);
return rv;
}
public static Xot_defn_tmpl Load_defn(Xowe_wiki wiki, Xop_ctx ctx, Xot_invk_tkn invk_tkn, Xoa_ttl ttl, byte[] name_ary) {
Xow_page_cache_itm tmpl_page_itm = wiki.Cache_mgr().Page_cache().Get_or_load_as_itm(ttl);
byte[] tmpl_page_bry = tmpl_page_itm == null ? null : tmpl_page_itm.Wtxt__direct();
Xot_defn_tmpl rv = null;
if (tmpl_page_bry != null) {
byte old_parse_tid = ctx.Parse_tid(); // NOTE: reusing ctxs is a bad idea; will change Parse_tid and cause strange errors; however, keeping for PERF reasons
Xow_ns ns_tmpl = wiki.Ns_mgr().Ns_template();
rv = wiki.Parser_mgr().Main().Parse_text_to_defn_obj(ctx, ctx.Tkn_mkr(), ns_tmpl, name_ary, tmpl_page_bry);
Xoa_ttl tmpl_page_ttl = tmpl_page_itm.Ttl();
byte[] frame_ttl = Bry_.Add(Xow_ns_canonical_.To_canonical_or_local_as_bry(tmpl_page_ttl.Ns()), Byte_ascii.Colon_bry, tmpl_page_ttl.Page_txt()); // NOTE: (1) must have ns (Full); (2) must be txt (space, not underscore); EX:Template:Location map+; DATE:2014-08-22; (3) must be canonical; DATE:2015-11-09
rv.Frame_ttl_(frame_ttl); // set defn's frame_ttl; needed for redirect_trg; PAGE:en.w:Statutory_city; DATE:2014-08-22
ctx.Parse_tid_(old_parse_tid);
wiki.Cache_mgr().Defn_cache().Add(rv, ns_tmpl.Case_match());
}
return rv;
}
private static void Print_not_found__by_transclude(Bry_bfr bfr, Xow_ns_mgr ns_mgr, boolean name_has_template, byte[] name_ary) {// print missing as [[Missing]]; PAGE:en.d:a DATE:2016-06-24
bfr.Add(Xop_tkn_.Lnki_bgn);
if (name_has_template)
bfr.Add(ns_mgr.Ns_template().Name_db()).Add_byte(Byte_ascii.Colon);
bfr.Add(name_ary);
bfr.Add(Xop_tkn_.Lnki_end);
}
public static void Print_not_found__w_template(Bry_bfr bfr, Xow_ns_mgr ns_mgr, byte[] name_ary) { // print missing as [[:Template:Missing]]; REF:MW: Parser.php|braceSubstitution|$text = "[[:$titleText]]"; EX:en.d:Kazakhstan; DATE:2014-03-25
bfr.Add(Xop_tkn_.Lnki_bgn).Add_byte(Byte_ascii.Colon);
bfr.Add(ns_mgr.Ns_template().Name_db()).Add_byte(Byte_ascii.Colon);
bfr.Add(name_ary).Add(Xop_tkn_.Lnki_end);
}
private boolean SubEval(Xop_ctx ctx, Xowe_wiki wiki, Bry_bfr bfr, byte[] name_ary, Xot_invk caller, byte[] src_for_tkn) {
Xoa_ttl page_ttl = Xoa_ttl.Parse(wiki, name_ary); if (page_ttl == null) return false; // ttl not valid; EX: {{:[[abc]]}}
Xot_defn_tmpl transclude_tmpl = null;
@@ -470,19 +420,18 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk {
arg.Tkn_grp_(this, args_len);
args_len = newLen;
} Arg_nde_tkn[] args = Arg_nde_tkn.Ary_empty; int args_max;
Arg_nde_tkn[] Resize(Arg_nde_tkn[] src, int cur_len, int new_len) {
private Arg_nde_tkn[] Resize(Arg_nde_tkn[] src, int cur_len, int new_len) {
Arg_nde_tkn[] rv = new Arg_nde_tkn[new_len];
Array_.Copy_to(src, 0, rv, 0, cur_len);
return rv;
}
public Xot_invk_tkn(int bgn, int end) {this.Tkn_ini_pos(false, bgn, end);}
@Override public byte Tkn_tid() {return typeId;} private byte typeId = Xop_tkn_itm_.Tid_tmpl_invk;
public void Tkn_tid_to_txt() {typeId = Xop_tkn_itm_.Tid_txt;}
byte[] Get_first_subst_itm(Xol_kwd_mgr kwd_mgr) {
private byte[] Get_first_subst_itm(Xol_kwd_mgr kwd_mgr) {
Xol_kwd_grp grp = kwd_mgr.Get_at(Xol_kwd_grp_.Id_subst); if (grp == null) return Bry_.Empty;
Xol_kwd_itm[] itms = grp.Itms();
return itms.length == 0 ? Bry_.Empty : itms[0].Val();
}
private static final Hash_adp_bry ignore_hash = Hash_adp_bry.ci_a7().Add_str_obj("Citation needed{{subst", "").Add_str_obj("Clarify{{subst", ""); // ignore SafeSubst templates
public static boolean Cache_enabled = false;
}
/*
NOTE_1: if (finder.Colon_pos() != -1) colon_pos = finder.Func().Name().length;

View File

@@ -0,0 +1,81 @@
/*
XOWA: the XOWA Offline Wiki Application
Copyright (C) 2012 gnosygnu@gmail.com
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as
published by the Free Software Foundation, either version 3 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 Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package gplx.xowa.parsers.tmpls; import gplx.*; import gplx.xowa.*; import gplx.xowa.parsers.*;
import gplx.xowa.langs.kwds.*;
import gplx.xowa.xtns.pfuncs.*;
import gplx.xowa.wikis.nss.*; import gplx.xowa.wikis.caches.*;
public class Xot_invk_tkn_ {
public static void Eval_func(Xop_ctx ctx, byte[] src, Xot_invk caller, Xot_invk invk, Bry_bfr bfr, Xot_defn defn, byte[] argx_ary) {
Pf_func_base defn_func = (Pf_func_base)defn;
int defn_func_id = defn_func.Id();
defn_func = (Pf_func_base)defn_func.New(defn_func_id, defn_func.Name()); // NOTE: always make copy b/c argx_ary may be dynamic
if (argx_ary != Bry_.Empty) defn_func.Argx_dat_(argx_ary);
defn_func.Eval_argx(ctx, src, caller, invk);
if (defn_func_id == Xol_kwd_grp_.Id_invoke) // NOTE: if #invoke, set frame_ttl to argx, not name; EX:{{#invoke:A}}
invk.Frame_ttl_(Bry_.Add(Xow_ns_.Bry__module_w_colon, Xoa_ttl.Replace_unders(defn_func.Argx_dat()))); // NOTE: always prepend "Module:" to frame_ttl; DATE:2014-06-13; NOTE: always use spaces; DATE:2014-08-14; always use canonical English "Module"; DATE:2015-11-09
Bry_bfr bfr_func = Bry_bfr_.New();
defn_func.Func_evaluate(bfr_func, ctx, caller, invk, src);
if (caller.Rslt_is_redirect()) // do not prepend if page is redirect; EX:"#REDIRECT" x> "\n#REDIRECT" DATE:2014-07-11
caller.Rslt_is_redirect_(false); // reset flag; needed for TEST; kludgy, but Rslt_is_redirect is intended for single use
else
ctx.Page().Tmpl_prepend_mgr().End(ctx, bfr, bfr_func.Bfr(), bfr_func.Len(), Bool_.N);
bfr.Add_bfr_and_clear(bfr_func);
}
public static void Bld_key(Xot_invk invk, byte[] name_ary, Bry_bfr bfr) {
bfr.Clear();
bfr.Add(name_ary);
int args_len = invk.Args_len();
for (int i = 0; i < args_len; i++) {
Arg_nde_tkn nde = invk.Args_get_by_idx(i);
bfr.Add_byte(Byte_ascii.Pipe);
if (nde.KeyTkn_exists()) {
bfr.Add(nde.Key_tkn().Dat_ary());
bfr.Add_byte(Byte_ascii.Eq);
}
bfr.Add(nde.Val_tkn().Dat_ary());
}
}
public static Xot_defn_tmpl Load_defn(Xowe_wiki wiki, Xop_ctx ctx, Xot_invk_tkn invk_tkn, Xoa_ttl ttl, byte[] name_ary) { // recursive loading of templates
Xow_page_cache_itm tmpl_page_itm = wiki.Cache_mgr().Page_cache().Get_or_load_as_itm(ttl);
byte[] tmpl_page_bry = tmpl_page_itm == null ? null : tmpl_page_itm.Wtxt__direct();
Xot_defn_tmpl rv = null;
if (tmpl_page_bry != null) {
byte old_parse_tid = ctx.Parse_tid(); // NOTE: reusing ctxs is a bad idea; will change Parse_tid and cause strange errors; however, keeping for PERF reasons
Xow_ns ns_tmpl = wiki.Ns_mgr().Ns_template();
rv = wiki.Parser_mgr().Main().Parse_text_to_defn_obj(ctx, ctx.Tkn_mkr(), ns_tmpl, name_ary, tmpl_page_bry);
Xoa_ttl tmpl_page_ttl = tmpl_page_itm.Ttl();
byte[] frame_ttl = Bry_.Add(Xow_ns_canonical_.To_canonical_or_local_as_bry(tmpl_page_ttl.Ns()), Byte_ascii.Colon_bry, tmpl_page_ttl.Page_txt()); // NOTE: (1) must have ns (Full); (2) must be txt (space, not underscore); EX:Template:Location map+; DATE:2014-08-22; (3) must be canonical; DATE:2015-11-09
rv.Frame_ttl_(frame_ttl); // set defn's frame_ttl; needed for redirect_trg; PAGE:en.w:Statutory_city; DATE:2014-08-22
ctx.Parse_tid_(old_parse_tid);
wiki.Cache_mgr().Defn_cache().Add(rv, ns_tmpl.Case_match());
}
return rv;
}
public static void Print_not_found__by_transclude(Bry_bfr bfr, Xow_ns_mgr ns_mgr, boolean name_has_template, byte[] name_ary) {// print missing as [[Missing]]; PAGE:en.d:a DATE:2016-06-24
bfr.Add(Xop_tkn_.Lnki_bgn);
if (name_has_template)
bfr.Add(ns_mgr.Ns_template().Name_db()).Add_byte(Byte_ascii.Colon);
bfr.Add(name_ary);
bfr.Add(Xop_tkn_.Lnki_end);
}
public static void Print_not_found__w_template(Bry_bfr bfr, Xow_ns_mgr ns_mgr, byte[] name_ary) { // print missing as [[:Template:Missing]]; REF:MW: Parser.php|braceSubstitution|$text = "[[:$titleText]]"; EX:en.d:Kazakhstan; DATE:2014-03-25
bfr.Add(Xop_tkn_.Lnki_bgn).Add_byte(Byte_ascii.Colon);
bfr.Add(ns_mgr.Ns_template().Name_db()).Add_byte(Byte_ascii.Colon);
bfr.Add(name_ary).Add(Xop_tkn_.Lnki_end);
}
}

View File

@@ -26,16 +26,19 @@ public class Xot_invk_wkr implements Xop_ctx_wkr, Xop_arg_wkr {
public int Make_tkn(Xop_ctx ctx, Xop_root_tkn root, byte[] src, int lxr_cur_pos, int lxr_end_pos, Xop_curly_bgn_tkn bgn_tkn, int keep_curly_bgn) {
Xot_invk_tkn invk = tkn_mkr.Tmpl_invk(bgn_tkn.Src_bgn(), lxr_end_pos);
int loop_bgn = bgn_tkn.Tkn_sub_idx() + 1, loop_end = root.Subs_len();
if (loop_bgn == loop_end) { // empty template; EX: "{{}}"
root.Subs_del_after(bgn_tkn.Tkn_sub_idx()); // del invk_bgn_tkn
root.Subs_add(tkn_mkr.Txt(bgn_tkn.Src_bgn(), lxr_end_pos));
ctx.Msg_log().Add_itm_none(Xop_tmpl_log.Tmpl_is_empty, src, bgn_tkn.Src_bgn(), lxr_end_pos);
// handle empty template; EX: "{{}}"
if (loop_bgn == loop_end) {
root.Subs_del_after(bgn_tkn.Tkn_sub_idx()); // del invk_bgn_tkn
root.Subs_add(tkn_mkr.Txt(bgn_tkn.Src_bgn(), lxr_end_pos)); // add txt tkn
return lxr_cur_pos;
}
// make arguments
boolean made = arg_bldr.Bld(ctx, tkn_mkr, this, Xop_arg_wkr_.Typ_tmpl, root, invk, lxr_cur_pos, lxr_end_pos, loop_bgn, loop_end, src);
Arg_itm_tkn key_tkn = invk.Name_tkn().Key_tkn();
if (!made
|| (key_tkn.Dat_bgn() == key_tkn.Dat_end() && key_tkn.Dat_bgn() != -1)) { // key_tkn is entirely whitespace; EX: {{\n}}
if ( !made // invalid args;
|| (key_tkn.Dat_bgn() == key_tkn.Dat_end() && key_tkn.Dat_bgn() != -1)) { // key_tkn is entirely whitespace; EX: {{\n}}
invk.Tkn_tid_to_txt();
ctx.Subs_add(root, tkn_mkr.Txt(lxr_cur_pos, lxr_end_pos));
return lxr_cur_pos;
@@ -61,7 +64,6 @@ public class Xot_invk_wkr implements Xop_ctx_wkr, Xop_arg_wkr {
if (key_tkn.Itm_static() != Bool_.Y_byte) return; // dynamic tkn; can't identify func/name
int colon_pos = -1, txt_bgn = key_tkn.Dat_bgn(), txt_end = key_tkn.Dat_end();
Xol_func_itm finder = new Xol_func_itm(); // TS.MEM: DATE:2016-07-12
ctx.Wiki().Lang().Func_regy().Find_defn(finder, src, txt_bgn, txt_end);
Xot_defn finder_func = finder.Func();

View File

@@ -22,10 +22,8 @@ public class Xot_tmpl_wtr {
public byte[] Write_all(Xop_ctx ctx, Xop_root_tkn root, byte[] src) {
// synchronized (this) { // THREAD:added synchronized after "failed to write tkn" DATE:2015-04-29
Bry_bfr rslt_bfr = ctx.Wiki().Utl__bfr_mkr().Get_m001();
ctx.Tmpl_output_(rslt_bfr);
rslt_bfr.Reset_if_gt(Io_mgr.Len_mb);
Write_tkn(ctx, src, src.length, rslt_bfr, root);
ctx.Tmpl_output_(null);
return rslt_bfr.To_bry_and_rls();
// }
}