From eddb6bebc79de5900a3d85071a282b1751afeb71 Mon Sep 17 00:00:00 2001 From: gnosygnu Date: Sun, 26 Oct 2014 22:13:39 -0400 Subject: [PATCH] v1.10.4.1 --- 100_core/src_110_primitive/gplx/Bry_.java | 1 + 100_core/src_120_basicDataType/gplx/Enm_.java | 2 + .../src_900_xml/gplx/Base64_utl.java | 9 +- 150_gfui/xtn/gplx/gfui/Swt_core_lnrs.java | 2 + 400_xowa/src/gplx/html/Html_utl.java | 1 - 400_xowa/src/gplx/xowa/Xoa_app_.java | 2 +- .../gplx/xowa/bldrs/files/Xob_fsdb_make.java | 10 +- .../xowa/bldrs/files/Xob_lnki_temp_wkr.java | 6 +- .../gplx/xowa/files/fsdb/Xof_fsdb_mgr_.java | 6 +- .../xowa/gui/views/Xog_tab_itm_edit_mgr.java | 3 +- .../src/gplx/xowa/hdumps/Xob_hdump_bldr.java | 88 +++++----- .../src/gplx/xowa/hdumps/Xodb_hdump_mgr.java | 24 ++- .../xowa/hdumps/Xodb_hdump_mgr__save_tst.java | 64 +++---- .../xowa/hdumps/Xodb_hdump_mgr_setup.java | 5 +- .../src/gplx/xowa/hdumps/Xodbv_page_tbl.java | 17 +- .../src/gplx/xowa/hdumps/Xowd_hdump_mgr.java | 9 + .../gplx/xowa/hdumps/core/Hdump_img_bldr.java | 2 +- .../xowa/hdumps/core/Hdump_module_mgr.java | 6 + .../src/gplx/xowa/hdumps/core/Hdump_page.java | 24 +++ ..._row.java => Xodb_wiki_page_html_row.java} | 11 +- ..._tbl.java => Xodb_wiki_page_html_tbl.java} | 49 +++--- ....java => Xodb_wiki_page_html_tbl_mem.java} | 8 +- .../xowa/hdumps/htmls/Hdump_html_consts.java | 4 +- .../gplx/xowa/hdumps/hzips/Xoa_hzip_dict.java | 34 ++++ .../xowa/hdumps/hzips/Xoa_hzip_itm__lnki.java | 110 ++++++++++++ .../hdumps/hzips/Xoa_hzip_itm__lnki_tst.java | 118 +++++++++++++ .../gplx/xowa/hdumps/hzips/Xoa_hzip_mgr.java | 93 +++++++++++ .../xowa/hdumps/loads/Hdump_load_mgr.java | 16 +- .../xowa/hdumps/loads/Hdump_load_mgr_tst.java | 32 ++-- .../hdumps/loads/Hdump_page_body_srl.java | 6 +- .../xowa/hdumps/saves/Hdump_save_mgr.java | 68 +++++++- .../gplx/xowa/hdumps/srls/Hpg_srl_itm.java | 156 ++++++++++++++++++ .../xowa/hdumps/srls/Hpg_srl_itm__tst.java | 52 ++++++ .../xowa/hdumps/srls/Hpg_srl_itm_tst.java | 99 +++++++++++ .../gplx/xowa/hdumps/srls/Hpg_srl_mgr.java | 40 +++++ 400_xowa/src/gplx/xowa/html/Xoh_html_wtr.java | 6 +- .../src/gplx/xowa/html/Xoh_page_wtr_wkr.java | 2 +- .../gplx/xowa/html/lnkis/Xoh_lnki_wtr.java | 17 +- .../src/gplx/xowa/html/tocs/Xow_toc_mgr.java | 2 +- .../gplx/xowa/html/tocs/Xow_toc_mgr_tst.java | 2 +- .../gplx/xowa/pages/Xopg_revision_data.java | 26 +++ .../Xop_lnki_logger_redlinks_mgr.java | 2 +- .../src/gplx/xowa/xtns/imaps/Imap_parser.java | 82 +++------ .../gplx/xowa/xtns/imaps/Imap_parser_tst.java | 1 + .../xtns/pfuncs/pages/Pfunc_rev_props.java | 9 +- .../pfuncs/pages/Pfunc_rev_props_tst.java | 4 +- .../src/gplx/xowa/xtns/poems/Poem_nde.java | 6 +- .../gplx/xowa/xtns/poems/Poem_nde_tst.java | 2 +- .../gplx/xowa/xtns/scribunto/Scrib_core.java | 3 +- .../scribunto/lib/Scrib_lib_wikibase_srl.java | 14 +- .../lib/Scrib_lib_wikibase_srl_tst.java | 38 ++++- .../lib/Scrib_lib_wikibase_srl_visitor.java | 2 +- .../xowa/xtns/wdatas/Wdata_wiki_mgr_fxt.java | 4 +- .../xtns/wdatas/Wdata_xwiki_link_wtr.java | 29 ++-- .../xtns/wdatas/Wdata_xwiki_link_wtr_tst.java | 22 ++- .../xtns/wdatas/core/Wdata_sitelink_itm.java | 1 + .../src_120_wiki/gplx/xowa/Xow_lang_grp.java | 20 +-- .../src_120_wiki/gplx/xowa/Xow_lang_itm.java | 5 +- .../src_120_wiki/gplx/xowa/Xow_lang_mgr.java | 44 ++++- .../gplx/xowa/Xow_lang_mgr_fxt.java | 2 +- .../gplx/xowa/Xow_lang_mgr_tst.java | 18 +- .../gplx/xowa/Xof_xfer_queue.java | 1 + 400_xowa/src_300_html/gplx/xowa/Xoa_page.java | 8 +- .../gplx/xowa/Xoa_revision_data.java | 27 --- .../gplx/xowa/Xoh_href_parser.java | 10 +- .../gplx/xowa/Xop_lnki_wkr__xwiki_tst.java | 10 +- .../src_490_xnde/gplx/xowa/Xop_xnde_wkr.java | 10 +- .../xowa/Xop_xnde_wkr__err_malformed_tst.java | 7 +- .../Xop_xnde_wkr__include_uncommon_tst.java | 2 +- .../src_500_tmpl/gplx/xowa/Xop_subst_tst.java | 9 +- .../src_500_tmpl/gplx/xowa/Xot_invk_tkn.java | 7 +- 71 files changed, 1265 insertions(+), 366 deletions(-) rename 400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_row_tid.java => 100_core/src_900_xml/gplx/Base64_utl.java (78%) rename 400_xowa/src/gplx/xowa/hdumps/dbs/{Hdump_text_row.java => Xodb_wiki_page_html_row.java} (65%) rename 400_xowa/src/gplx/xowa/hdumps/dbs/{Hdump_text_tbl.java => Xodb_wiki_page_html_tbl.java} (61%) rename 400_xowa/src/gplx/xowa/hdumps/dbs/{Hdump_text_tbl_mem.java => Xodb_wiki_page_html_tbl_mem.java} (79%) create mode 100644 400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_dict.java create mode 100644 400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_itm__lnki.java create mode 100644 400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_itm__lnki_tst.java create mode 100644 400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_mgr.java create mode 100644 400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm.java create mode 100644 400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm__tst.java create mode 100644 400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm_tst.java create mode 100644 400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_mgr.java create mode 100644 400_xowa/src/gplx/xowa/pages/Xopg_revision_data.java delete mode 100644 400_xowa/src_300_html/gplx/xowa/Xoa_revision_data.java diff --git a/100_core/src_110_primitive/gplx/Bry_.java b/100_core/src_110_primitive/gplx/Bry_.java index b097fa723..4fdce853f 100644 --- a/100_core/src_110_primitive/gplx/Bry_.java +++ b/100_core/src_110_primitive/gplx/Bry_.java @@ -698,6 +698,7 @@ public class Bry_ { } public static float XtoFloatByPos(byte[] ary, int bgn, int end) {return Float_.parse_(String_.new_utf8_(ary, bgn, end));} public static double Xto_double(byte[] bry) {return Double_.parse_(String_.new_utf8_(bry, 0, bry.length));} + public static double Xto_double_or(byte[] bry, double or) {return Double_.parseOr_(String_.new_utf8_(bry, 0, bry.length), or);} public static double XtoDoubleByPosOr(byte[] ary, int bgn, int end, double or) {return Double_.parseOr_(String_.new_utf8_(ary, bgn, end), or);} public static double XtoDoubleByPos(byte[] ary, int bgn, int end) {return Double_.parse_(String_.new_utf8_(ary, bgn, end));} public static DecimalAdp XtoDecimalByPos(byte[] ary, int bgn, int end) {return DecimalAdp_.parse_(String_.new_utf8_(ary, bgn, end));} diff --git a/100_core/src_120_basicDataType/gplx/Enm_.java b/100_core/src_120_basicDataType/gplx/Enm_.java index 3531f032a..a5be6491e 100644 --- a/100_core/src_120_basicDataType/gplx/Enm_.java +++ b/100_core/src_120_basicDataType/gplx/Enm_.java @@ -24,5 +24,7 @@ public class Enm_ { boolean has = find == (val & find); return (has ^ enable) ? val ^ find : val; } + public static boolean Has_byte(byte val, byte find) {return find == (val & find);} + public static byte Add_byte(byte flag, byte itm) {return (byte)(flag | itm);} static int Ordinal_lang(Object v) {return ((Enum)v).ordinal();} } diff --git a/400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_row_tid.java b/100_core/src_900_xml/gplx/Base64_utl.java similarity index 78% rename from 400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_row_tid.java rename to 100_core/src_900_xml/gplx/Base64_utl.java index 618029ba8..681c0f580 100644 --- a/400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_row_tid.java +++ b/100_core/src_900_xml/gplx/Base64_utl.java @@ -15,7 +15,10 @@ 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 . */ -package gplx.xowa.hdumps.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; -public class Hdump_text_row_tid { // NOTE: SERIALIZED - public static final int Tid_body = 0, Tid_data = 1; +package gplx; +public class Base64_utl { + public static void Encode(Bry_bfr bfr, byte[] bry, int bgn, int end) { + for (int i = bgn; i < end; ++i) { + } + } } diff --git a/150_gfui/xtn/gplx/gfui/Swt_core_lnrs.java b/150_gfui/xtn/gplx/gfui/Swt_core_lnrs.java index 2181329f0..b87367878 100644 --- a/150_gfui/xtn/gplx/gfui/Swt_core_lnrs.java +++ b/150_gfui/xtn/gplx/gfui/Swt_core_lnrs.java @@ -93,6 +93,8 @@ class Swt_lnr_key implements KeyListener { case 16777235: val = IptKey_.F10.Val(); break; case 16777236: val = IptKey_.F11.Val(); break; case 16777237: val = IptKey_.F12.Val(); break; + case 16777259: val = IptKey_.Equal.Val(); break; + case 16777261: val = IptKey_.Minus.Val(); break; case 16777300: val = IptKey_.ScrollLock.Val(); break; case 16777301: val = IptKey_.Pause.Val(); break; case 327680: val = IptKey_.Insert.Val(); break; diff --git a/400_xowa/src/gplx/html/Html_utl.java b/400_xowa/src/gplx/html/Html_utl.java index 38d2df616..4b4a63805 100644 --- a/400_xowa/src/gplx/html/Html_utl.java +++ b/400_xowa/src/gplx/html/Html_utl.java @@ -54,7 +54,6 @@ public class Html_utl { public static byte[] Escape_html_as_bry(byte[] bry) {return Escape_html(false, Bry_bfr.new_(), bry, 0, bry.length, true, true, true, true, true);} public static byte[] Escape_html_as_bry(byte[] bry, boolean lt, boolean gt, boolean amp, boolean quote, boolean apos) {return Escape_html(false, Bry_bfr.new_(), bry, 0, bry.length, lt, gt, amp, quote, apos);} - public static void Escape_html_to_bfr(Bry_bfr bfr, byte[] bry, int bgn, int end, boolean escape_lt, boolean escape_gt, boolean escape_amp, boolean escape_quote, boolean escape_apos) { Escape_html(true, bfr, bry, bgn, end, escape_lt, escape_gt, escape_amp, escape_quote, escape_apos); } diff --git a/400_xowa/src/gplx/xowa/Xoa_app_.java b/400_xowa/src/gplx/xowa/Xoa_app_.java index 2996a368a..4379195b9 100644 --- a/400_xowa/src/gplx/xowa/Xoa_app_.java +++ b/400_xowa/src/gplx/xowa/Xoa_app_.java @@ -24,7 +24,7 @@ public class Xoa_app_ { boot_mgr.Run(args); } public static final String Name = "xowa"; - public static final String Version = "1.10.3.1"; + public static final String Version = "1.10.4.1"; public static String Build_date = "2012-12-30 00:00:00"; public static String Op_sys; public static String User_agent = ""; diff --git a/400_xowa/src/gplx/xowa/bldrs/files/Xob_fsdb_make.java b/400_xowa/src/gplx/xowa/bldrs/files/Xob_fsdb_make.java index a4a3ecca7..9525ebb0b 100644 --- a/400_xowa/src/gplx/xowa/bldrs/files/Xob_fsdb_make.java +++ b/400_xowa/src/gplx/xowa/bldrs/files/Xob_fsdb_make.java @@ -22,7 +22,7 @@ public class Xob_fsdb_make extends Xob_itm_basic_base implements Xob_cmd { private int select_interval = 2500, progress_interval = 1, commit_interval = 1, delete_interval = 5000; private int exec_count, exec_count_max = Int_.MaxValue; private int exec_fail, exec_fail_max = 2000; // 115 over 900k - private boolean exec_done; + private boolean exec_done, resume_enabled = false; private int page_id_bmk = -1, lnki_id_bmk = -1; private int page_id_val = -1, lnki_id_val = -1; private int page_id_end = Int_.MaxValue; @@ -128,6 +128,10 @@ public class Xob_fsdb_make extends Xob_itm_basic_base implements Xob_cmd { db_select_stmt = Xob_xfer_regy_tbl.Select_by_page_id_stmt(provider); } private boolean Init_bmk(Xodb_xowa_cfg_tbl tbl_cfg) { + if (!resume_enabled) { // clear cfg entries if resume disabled; note that disabled by default; DATE:2014-10-24 + tbl_cfg.Delete(Cfg_fsdb_make, Cfg_page_id_bmk); + tbl_cfg.Delete(Cfg_fsdb_make, Cfg_lnki_id_bmk); + } String page_id_str = tbl_cfg.Select_val(Cfg_fsdb_make, Cfg_page_id_bmk); if (page_id_str == null) { // bmks not found; new db; insert; tbl_cfg.Insert_str(Cfg_fsdb_make, Cfg_page_id_bmk , Int_.Xto_str(page_id_bmk)); @@ -286,6 +290,7 @@ public class Xob_fsdb_make extends Xob_itm_basic_base implements Xob_cmd { else if (ctx.Match(k, Invk_app_restart_enabled_)) app_restart_enabled = m.ReadBool("v"); else if (ctx.Match(k, Invk_db_restart_tries_max_)) db_reset_tries_max = m.ReadInt("v"); else if (ctx.Match(k, Invk_trg_fsdb_mgr)) return trg_fsdb_mgr; + else if (ctx.Match(k, Invk_resume_enabled_)) resume_enabled = m.ReadYn("v"); else return GfoInvkAble_.Rv_unhandled; return this; } @@ -298,7 +303,8 @@ public class Xob_fsdb_make extends Xob_itm_basic_base implements Xob_cmd { , Invk_delete_interval_ = "delete_interval_" , Invk_app_restart_enabled_ = "app_restart_enabled_" , Invk_db_restart_tries_max_ = "db_restart_tries_max_" - , Invk_trg_fsdb_mgr = "trg_fsdb_mgr" + , Invk_trg_fsdb_mgr = "trg_fsdb_mgr" + , Invk_resume_enabled_ = "resume_enabled_" ; public static byte Status_null = 0, Status_pass = 1, Status_fail = 2; } diff --git a/400_xowa/src/gplx/xowa/bldrs/files/Xob_lnki_temp_wkr.java b/400_xowa/src/gplx/xowa/bldrs/files/Xob_lnki_temp_wkr.java index 795b5a397..33d03a5fb 100644 --- a/400_xowa/src/gplx/xowa/bldrs/files/Xob_lnki_temp_wkr.java +++ b/400_xowa/src/gplx/xowa/bldrs/files/Xob_lnki_temp_wkr.java @@ -69,21 +69,21 @@ public class Xob_lnki_temp_wkr extends Xob_dump_mgr_base implements Xop_lnki_log trg_mnt_mgr.Insert_to_mnt_(Fsdb_mnt_mgr.Mnt_idx_main); Fsdb_mnt_mgr.Patch(trg_mnt_mgr); // NOTE: see fsdb_make; DATE:2014-04-26 if (gen_hdump) { - hdump_bldr = new Xob_hdump_bldr(wiki, provider, hdump_max); + hdump_bldr = new Xob_hdump_bldr(wiki.Db_mgr_as_sql(), provider, hdump_max); + hdump_bldr.Bld_init(); } provider.Txn_mgr().Txn_bgn_if_none(); log_mgr.Txn_bgn(); } @Override public void Exec_pg_itm_hook(Xow_ns ns, Xodb_page db_page, byte[] page_src) { Xoa_ttl ttl = Xoa_ttl.parse_(wiki, ns.Gen_ttl(db_page.Ttl_wo_ns())); - // Io_mgr._.AppendFilStr("C:\\debug.txt", String_.new_utf8_(ttl.Full_txt()) + "\n"); byte[] ttl_bry = ttl.Page_db(); byte page_tid = Xow_page_tid.Identify(wiki.Domain_tid(), ns.Id(), ttl_bry); if (page_tid != Xow_page_tid.Tid_wikitext) return; // ignore js, css, lua, json Xoa_page page = ctx.Cur_page(); page.Clear(); page.Ttl_(ttl).Revision_data().Id_(db_page.Id()); - page.Lnki_redlinks_mgr().Page_bgn(); + page.Lnki_redlinks_mgr().Clear(); if (ns.Id_tmpl()) parser.Parse_text_to_defn_obj(ctx, ctx.Tkn_mkr(), wiki.Ns_mgr().Ns_template(), ttl_bry, page_src); else { diff --git a/400_xowa/src/gplx/xowa/files/fsdb/Xof_fsdb_mgr_.java b/400_xowa/src/gplx/xowa/files/fsdb/Xof_fsdb_mgr_.java index 42f964ded..1ccec8700 100644 --- a/400_xowa/src/gplx/xowa/files/fsdb/Xof_fsdb_mgr_.java +++ b/400_xowa/src/gplx/xowa/files/fsdb/Xof_fsdb_mgr_.java @@ -27,7 +27,7 @@ public class Xof_fsdb_mgr_ { for (int i = 0; i < itms_len; i++) { if (usr_dlg.Canceled()) return; Xof_fsdb_itm itm = (Xof_fsdb_itm)itms.FetchAt(i); - Itm_process(fsdb_mgr, file_dir, usr_dlg, itm, fsdb_list, repo_mgr, url_bldr, exec_tid); + Itm_process(fsdb_mgr, page, file_dir, usr_dlg, itm, fsdb_list, repo_mgr, url_bldr, exec_tid); } itms_len = fsdb_list.Count(); if (itms_len == 0) return; // all items found; return; Reg_search(fsdb_mgr, file_dir, usr_dlg, page, exec_tid, fsdb_list, itms_len, repo_mgr); @@ -89,11 +89,11 @@ public class Xof_fsdb_mgr_ { ); } private Xof_img_size img_size = new Xof_img_size(); - private void Itm_process(Xof_fsdb_mgr fsdb_mgr, Io_url file_dir, Gfo_usr_dlg usr_dlg, Xof_fsdb_itm itm, ListAdp fsdb_list, Xow_repo_mgr repo_mgr, Xof_url_bldr url_bldr, byte exec_tid) { + private void Itm_process(Xof_fsdb_mgr fsdb_mgr, Xoa_page page, Io_url file_dir, Gfo_usr_dlg usr_dlg, Xof_fsdb_itm itm, ListAdp fsdb_list, Xow_repo_mgr repo_mgr, Xof_url_bldr url_bldr, byte exec_tid) { switch (itm.Rslt_reg()) { case Xof_wiki_orig_wkr_.Tid_found_orig: itm.Html__init(repo_mgr, url_bldr, img_size, exec_tid); - // Js_img_mgr.Update_img(usr_dlg, itm); // DELETE: DATE:2014-02-01 + Js_img_mgr.Update_img(page, itm); // NOTE: needed when opening 2+ tabs and missing image is on 2+ pages; 2nd page will have img as Xof_wiki_orig_wkr_.Tid_found_orig; DATE:2014-10-20 if (!Env_.Mode_testing()) { Cache_fil_itm cache_fil_itm = fsdb_mgr.Cache_mgr().Reg(fsdb_mgr.Wiki(), itm, 0); if (cache_fil_itm.Fil_size() == 0) { diff --git a/400_xowa/src/gplx/xowa/gui/views/Xog_tab_itm_edit_mgr.java b/400_xowa/src/gplx/xowa/gui/views/Xog_tab_itm_edit_mgr.java index 956d3bf76..7dfcab29b 100644 --- a/400_xowa/src/gplx/xowa/gui/views/Xog_tab_itm_edit_mgr.java +++ b/400_xowa/src/gplx/xowa/gui/views/Xog_tab_itm_edit_mgr.java @@ -49,7 +49,7 @@ public class Xog_tab_itm_edit_mgr { byte[] new_text = Get_new_text(tab); Xoa_page new_page = Xoa_page.new_(wiki, page.Ttl()); - new_page.Revision_data().Id_(page.Revision_data().Id()); // NOTE: page_id needed for sqlite (was not needed for xdat) + new_page.Revision_data().Id_(page.Revision_data().Id()); // NOTE: page_id needed for sqlite (was not needed for xdat) new_page.Data_raw_(new_text); wiki.ParsePage_root(new_page, true); // refresh html tab.Page_(new_page); new_page.Tab_(tab); // replace old page with new_page; DATE:2014-10-09 @@ -77,6 +77,7 @@ public class Xog_tab_itm_edit_mgr { Xoa_page page = tab.Page(); Xow_wiki wiki = page.Wiki(); Xog_win_itm win_itm = tab.Tab_mgr().Win(); if (Bry_.Eq(page.Ttl().Page_db(), wiki.Props().Main_page())) { win_itm.Usr_dlg().Warn_many("", "", "The Main Page cannot be renamed"); + win_itm.Kit().Ask_ok("", "", "The Main Page cannot be renamed"); return; } byte[] new_text = Bry_.new_utf8_(tab.Html_itm().Get_elem_value(Xog_html_itm.Elem_id__xowa_edit_rename_box)); diff --git a/400_xowa/src/gplx/xowa/hdumps/Xob_hdump_bldr.java b/400_xowa/src/gplx/xowa/hdumps/Xob_hdump_bldr.java index 20f5fdc18..db45b58fe 100644 --- a/400_xowa/src/gplx/xowa/hdumps/Xob_hdump_bldr.java +++ b/400_xowa/src/gplx/xowa/hdumps/Xob_hdump_bldr.java @@ -16,67 +16,71 @@ You should have received a copy of the GNU Affero General Public License along with this program. If not, see . */ package gplx.xowa.hdumps; import gplx.*; import gplx.xowa.*; -import gplx.dbs.*; import gplx.xowa.dbs.*; import gplx.xowa.dbs.tbls.*; import gplx.xowa.hdumps.saves.*; import gplx.xowa.hdumps.dbs.*; +import gplx.dbs.*; import gplx.ios.*; import gplx.xowa.dbs.*; import gplx.xowa.dbs.tbls.*; import gplx.xowa.hdumps.saves.*; import gplx.xowa.hdumps.dbs.*; import gplx.xowa.hdumps.core.*; public class Xob_hdump_bldr { - private Bry_bfr tmp_bfr = Bry_bfr.reset_(Io_mgr.Len_mb); - private Xow_wiki wiki; private Xodb_file core_db; private Xodb_xowa_cfg_tbl cfg_tbl; private Db_stmt cfg_update_stmt; + private Xodb_fsys_mgr fsys_mgr; private Xodb_file core_db; private Xodb_xowa_db_tbl db_tbl; private Xodb_xowa_cfg_tbl cfg_tbl; private Db_stmt cfg_update_stmt; private int hdump_db_id; private long hdump_db_size, hdump_db_max; private Db_provider hdump_db_provider; private Xodb_hdump_mgr hdump_mgr; private Hdump_save_mgr hdump_save_mgr; - public Xob_hdump_bldr(Xow_wiki wiki, Db_provider make_provider, long hdump_db_max) { - this.wiki = wiki; this.hdump_db_max = hdump_db_max; - core_db = wiki.Db_mgr_as_sql().Fsys_mgr().Get_tid_root(Xodb_file_tid.Tid_core); - hdump_mgr = wiki.Db_mgr_as_sql().Hdump_mgr(); hdump_save_mgr = hdump_mgr.Save_mgr(); + public Xob_hdump_bldr(Xodb_mgr_sql db_mgr, Db_provider make_provider, long hdump_db_max) { + this.hdump_db_max = hdump_db_max; + this.fsys_mgr = db_mgr.Fsys_mgr(); + core_db = fsys_mgr.Get_tid_root(Xodb_file_tid.Tid_core); + db_tbl = db_mgr.Tbl_xowa_db(); cfg_tbl = new Xodb_xowa_cfg_tbl().Provider_(make_provider); cfg_update_stmt = cfg_tbl.Update_stmt(); Xodb_hdump_mgr_setup.Assert_col__page_html_db_id(core_db.Provider(), cfg_tbl); - Init_hdump_db(Db_get_last_or_make(wiki), cfg_tbl.Select_val_as_long_or(Cfg_grp_hdump_make, Cfg_itm_hdump_size, 0)); + hdump_mgr = db_mgr.Hdump_mgr(); hdump_save_mgr = hdump_mgr.Save_mgr(); + hdump_save_mgr.Hdump_stats_enable_y_(make_provider); + } + public void Bld_init() { + Db_init(Db_get_last_or_make(fsys_mgr), cfg_tbl.Select_val_as_long_or(Cfg_grp_hdump_make, Cfg_itm_hdump_size, 0)); hdump_db_provider.Txn_mgr().Txn_bgn_if_none(); } - public void Insert_page(Xoa_page page) { - hdump_mgr.Write(tmp_bfr, page); - int body_len = hdump_save_mgr.Insert_body(page, page.Revision_data().Id()); - hdump_db_size += body_len; - if (hdump_db_size > hdump_db_max) { - Db_term(core_db, hdump_db_provider, hdump_db_id); - Init_hdump_db(wiki.Db_mgr_as_sql().Fsys_mgr().Make(Xodb_file_tid.Tid_html), 0); - Db_init(hdump_db_provider); - } - } - public void Commit() { - Xodb_mgr_sql db_mgr = wiki.Db_mgr_as_sql(); db_mgr.Tbl_xowa_db().Commit_all(db_mgr.Fsys_mgr()); // commit new html_dbs - hdump_db_provider.Txn_mgr().Txn_end_all_bgn_if_none(); - cfg_tbl.Update(cfg_update_stmt, Cfg_grp_hdump_make, Cfg_itm_hdump_size, Long_.Xto_str(hdump_db_size)); - } public void Bld_term() { this.Commit(); Db_term(core_db, hdump_db_provider, hdump_db_id); } - private void Init_hdump_db(Xodb_file db_file, long hdump_db_size) { - this.hdump_db_id = db_file.Id(); - this.hdump_db_provider = db_file.Provider(); - this.hdump_db_size = hdump_db_size; - this.hdump_save_mgr.Tbl().Provider_(hdump_db_provider); - } - private static Xodb_file Db_get_last_or_make(Xow_wiki wiki) { - Xodb_fsys_mgr fsys_mgr = wiki.Db_mgr_as_sql().Fsys_mgr(); - Xodb_file rv = fsys_mgr.Get_tid_root(Xodb_file_tid.Tid_html); - if (rv == null) { - rv = fsys_mgr.Make(Xodb_file_tid.Tid_html); - Db_init(rv.Provider()); + private Bry_bfr tmp_bfr = Bry_bfr.reset_(Io_mgr.Len_mb); + public void Insert_page(Xoa_page page) { + hdump_mgr.Write2(tmp_bfr, page); + hdump_db_size += hdump_save_mgr.Insert_body(page, page.Revision_data().Id()); + if (hdump_db_size > hdump_db_max) { + Db_term(core_db, hdump_db_provider, hdump_db_id); + Db_init(Db_make(fsys_mgr), 0); } + } + public void Commit() { + db_tbl.Commit_all(fsys_mgr); // commit new html_dbs + hdump_db_provider.Txn_mgr().Txn_end_all_bgn_if_none(); // commit entries + cfg_tbl.Update(cfg_update_stmt, Cfg_grp_hdump_make, Cfg_itm_hdump_size, Long_.Xto_str(hdump_db_size)); // update cfg; should happen after commit entries + } + private static Xodb_file Db_get_last_or_make(Xodb_fsys_mgr fsys_mgr) { + Xodb_file rv = fsys_mgr.Get_tid_root(Xodb_file_tid.Tid_html); + if (rv == null) rv = Db_make(fsys_mgr); + return rv; + } + private void Db_init(Xodb_file db_file, long hdump_db_size) { + this.hdump_db_id = db_file.Id(); + this.hdump_db_size = hdump_db_size; + this.hdump_db_provider = db_file.Provider(); + this.hdump_save_mgr.Tbl().Provider_(hdump_db_provider); + } + private static Xodb_file Db_make(Xodb_fsys_mgr fsys_mgr) { + Xodb_file rv = fsys_mgr.Make(Xodb_file_tid.Tid_html); + rv.Provider().Exec_sql(Xodb_wiki_page_html_tbl.Tbl_sql); return rv; } - private static void Db_init(Db_provider p) {p.Exec_sql(Hdump_text_tbl.Tbl_sql);} private static void Db_term(Xodb_file core_db_file, Db_provider hdump_db_provider, int hdump_db_id) { - hdump_db_provider.Txn_mgr().Txn_end_all(); - Sqlite_engine_.Idx_create(hdump_db_provider, Hdump_text_tbl.Idx_core); - Sqlite_engine_.Db_attach(hdump_db_provider, "page_db", core_db_file.Url().Raw()); + hdump_db_provider.Txn_mgr().Txn_end_all(); // commit transactions + Sqlite_engine_.Idx_create(hdump_db_provider, Xodb_wiki_page_html_tbl.Idx_core); // create index + Sqlite_engine_.Db_attach(hdump_db_provider, "page_db", core_db_file.Url().Raw()); // update page_db.page with page_html_db_id hdump_db_provider.Txn_mgr().Txn_bgn(); - hdump_db_provider.Exec_sql(String_.Format(Sql_update_page, hdump_db_id)); // update all page_html_db_id entries in page_db + hdump_db_provider.Exec_sql(String_.Format(Sql_update_page_html_db_id, hdump_db_id)); hdump_db_provider.Txn_mgr().Txn_end(); Sqlite_engine_.Db_detach(hdump_db_provider, "page_db"); + hdump_db_provider.Conn_term(); // release provider } private static final String Cfg_grp_hdump_make = "hdump.make", Cfg_itm_hdump_size = "hdump.size"; - private static final String Sql_update_page = String_.Concat_lines_nl_skip_last + private static final String Sql_update_page_html_db_id = String_.Concat_lines_nl_skip_last ( "REPLACE INTO page_db.page (page_id, page_namespace, page_title, page_is_redirect, page_touched, page_len, page_random_int, page_file_idx, page_redirect_id, page_html_db_id)" , "SELECT p.page_id" , ", p.page_namespace" @@ -89,6 +93,6 @@ public class Xob_hdump_bldr { , ", p.page_redirect_id" , ", {0}" , "FROM page_db.page p" - , " JOIN html_text h ON p.page_id = h.page_id" + , " JOIN wiki_page_html h ON p.page_id = h.page_id" ); } diff --git a/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr.java b/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr.java index df93090a5..29fa1f17d 100644 --- a/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr.java +++ b/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr.java @@ -17,24 +17,25 @@ along with this program. If not, see . */ package gplx.xowa.hdumps; import gplx.*; import gplx.xowa.*; import gplx.dbs.*; import gplx.xowa.dbs.*; import gplx.xowa.html.*; import gplx.xowa.gui.*; -import gplx.xowa.hdumps.core.*; import gplx.xowa.hdumps.saves.*; import gplx.xowa.pages.*; import gplx.xowa.hdumps.loads.*; import gplx.xowa.hdumps.htmls.*; import gplx.xowa.hdumps.dbs.*; +import gplx.xowa.hdumps.core.*; import gplx.xowa.hdumps.saves.*; import gplx.xowa.pages.*; import gplx.xowa.hdumps.loads.*; import gplx.xowa.hdumps.htmls.*; import gplx.xowa.hdumps.dbs.*; import gplx.xowa.hdumps.hzips.*; public class Xodb_hdump_mgr { - private Xodb_file hdump_db_file; + private Xodb_file hdump_db_file; private Xoa_hzip_mgr hzip_mgr; public Xodb_hdump_mgr(Xow_wiki wiki) { this.wiki = wiki; load_mgr = new Hdump_load_mgr(); - Tbl_(new Hdump_text_tbl()); + Tbl_(new Xodb_wiki_page_html_tbl()); text_tbl.Init_by_wiki(wiki); Xoa_app app = wiki.App(); html_mgr.Init_by_app(app.Usr_dlg(), app.Fsys_mgr(), app.Encoder_mgr().Fsys()); + hzip_mgr = new Xoa_hzip_mgr(app.Usr_dlg(), wiki); } public Xow_wiki Wiki() {return wiki;} private final Xow_wiki wiki; @gplx.Internal protected Hdump_load_mgr Load_mgr() {return load_mgr;} private Hdump_load_mgr load_mgr; @gplx.Internal protected Hdump_save_mgr Save_mgr() {return save_mgr;} private Hdump_save_mgr save_mgr = new Hdump_save_mgr(); public Hdump_html_body Html_mgr() {return html_mgr;} private Hdump_html_body html_mgr = new Hdump_html_body(); - public Hdump_text_tbl Text_tbl() {return text_tbl;} private Hdump_text_tbl text_tbl; + public Xodb_wiki_page_html_tbl Text_tbl() {return text_tbl;} private Xodb_wiki_page_html_tbl text_tbl; public boolean Enabled() {return enabled;} public void Enabled_(boolean v) {enabled = v;} private boolean enabled; - @gplx.Internal protected void Tbl_mem_() {Tbl_(new Hdump_text_tbl_mem());} + @gplx.Internal protected void Tbl_mem_() {Tbl_(new Xodb_wiki_page_html_tbl_mem());} public int Html_db_id_default(int page_len) { return -1; } @@ -58,11 +59,22 @@ public class Xodb_hdump_mgr { wkr.Write_body(bfr, Xoh_wtr_ctx.Hdump, page); page.Hdump_data().Body_(bfr.Xto_bry_and_clear()); } + public void Write2(Bry_bfr tmp_bfr, Xoa_page page) { + page.File_queue().Clear(); // need to reset uid to 0, else xowa_file_# will resume from last + Xoh_page_wtr_wkr wkr = wiki.Html_mgr().Page_wtr_mgr().Wkr(Xopg_view_mode.Tid_read); + wkr.Write_body(tmp_bfr, Xoh_wtr_ctx.Hdump, page); + hzip_mgr.Save(tmp_bfr, page.Url().Xto_full_bry(), tmp_bfr.Xto_bry_and_clear()); + page.Hdump_data().Body_(tmp_bfr.Xto_bry_and_clear()); + hpg.Init(tmp_bfr, page); + } private Hdump_page hpg = new Hdump_page(); public void Load(Xow_wiki wiki, Xoa_page page, int html_db_id) { if (!Enabled_chk()) return; page.Root_(new Xop_root_tkn()); Hdump_page hpg = new Hdump_page().Init(page.Revision_data().Id(), page.Url(), page.Ttl()); load_mgr.Load(hpg, wiki.Db_mgr_as_sql().Fsys_mgr(), html_db_id, page.Revision_data().Id(), page.Ttl()); + Bry_bfr tmp_bfr = wiki.Utl_bry_bfr_mkr().Get_b512(); + hzip_mgr.Load(tmp_bfr, page.Url().Xto_full_bry(), hpg.Page_body()); + hpg.Page_body_(tmp_bfr.Mkr_rls().Xto_bry_and_clear()); Load_page(wiki, page, hpg); } private void Load_page(Xow_wiki wiki, Xoa_page page, Hdump_page hpg) { @@ -76,7 +88,7 @@ public class Xodb_hdump_mgr { Hdump_page_body_srl.Load_html_modules(html_data.Module_mgr(), hpg); tmp_bfr.Mkr_rls(); } - private void Tbl_(Hdump_text_tbl v) { + private void Tbl_(Xodb_wiki_page_html_tbl v) { text_tbl = v; save_mgr.Tbl_(text_tbl); // load_mgr.Tbl_(text_tbl); diff --git a/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr__save_tst.java b/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr__save_tst.java index eeffd1250..0807aa312 100644 --- a/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr__save_tst.java +++ b/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr__save_tst.java @@ -20,18 +20,18 @@ import org.junit.*; import gplx.dbs.*; import gplx.xowa.files.*; import gplx.xowa.hdumps.core.*; import gplx.xowa.hdumps.dbs.*; import gplx.xowa.hdumps.saves.*; import gplx.xowa.hdumps.loads.*; import gplx.xowa.hdumps.pages.*; public class Xodb_hdump_mgr__save_tst { @Before public void init() {fxt.Clear();} private Xodb_hdump_mgr__save_fxt fxt = new Xodb_hdump_mgr__save_fxt(); - @Test public void Body() { - fxt.Test_save("abc", fxt.Make_row_body(0, "abc")); - } - @Test public void Img() { - fxt.Test_save("a[[File:A.png|test_caption]]b[[File:B.png|test_caption]]" - , fxt.Make_row_body(2, "a\"test_caption\"b\"test_caption\"") - , fxt.Make_row_img - ( fxt.Make_xfer("A.png", 0, 0, 0, Bool_.Y, Xof_ext_.Id_png) - , fxt.Make_xfer("B.png", 1, 0, 0, Bool_.Y, Xof_ext_.Id_png) - ) - ); - } +// @Test public void Body() { +// fxt.Test_save("abc", fxt.Make_row_body(0, "abc")); +// } +// @Test public void Img() { +// fxt.Test_save("a[[File:A.png|test_caption]]b[[File:B.png|test_caption]]" +// , fxt.Make_row_body(2, "a\"test_caption\"b\"test_caption\"") +// , fxt.Make_row_img +// ( fxt.Make_xfer("A.png", 0, 0, 0, Bool_.Y, Xof_ext_.Id_png) +// , fxt.Make_xfer("B.png", 1, 0, 0, Bool_.Y, Xof_ext_.Id_png) +// ) +// ); +// } @Test public void Display_title() { fxt.Test_write("{{DISPLAYTITLE:A}}bcd", String_.Concat_lines_nl_skip_last ( "0|0" @@ -63,13 +63,13 @@ public class Xodb_hdump_mgr__save_tst { , "bcd" )); } - @Test public void Redlink() { - fxt.Init_redlinks(1); - fxt.Test_save("[[A]] [[B]]" - , fxt.Make_row_body(0, "A B") - , fxt.Make_row_redlink(1) - ); - } +// @Test public void Redlink() { +// fxt.Init_redlinks(1); +// fxt.Test_save("[[A]] [[B]]" +// , fxt.Make_row_body(0, "A B") +// , fxt.Make_row_redlink(1) +// ); +// } } class Xodb_hdump_mgr__save_fxt extends Xodb_hdump_mgr__base_fxt { private int page_id = 0; @@ -77,31 +77,31 @@ class Xodb_hdump_mgr__save_fxt extends Xodb_hdump_mgr__base_fxt { private ListAdp expd_rows = ListAdp_.new_(); @Override public void Clear_end() { hdump_mgr.Tbl_mem_(); - hdump_mgr.Text_tbl().Provider_(Hdump_text_tbl_mem.Null_provider); + hdump_mgr.Text_tbl().Provider_(Xodb_wiki_page_html_tbl_mem.Null_provider); init_redlinks = null; } public void Init_redlinks(int... uids) { this.init_redlinks = uids; - page.Lnki_redlinks_mgr().Page_bgn(); + page.Lnki_redlinks_mgr().Clear(); } private int[] init_redlinks; - public Hdump_text_row Make_row_body(int imgs_count, String body) { + public Xodb_wiki_page_html_row Make_row_body(int imgs_count, String body) { page.Hdump_data().Body_(Bry_.new_utf8_(body)); page.Hdump_data().Data_count_imgs_(imgs_count); Hdump_page_body_srl.Save(tmp_bfr, page); - return new Hdump_text_row(page_id, Hdump_text_row_tid.Tid_body, tmp_bfr.Xto_bry_and_clear()); + return new Xodb_wiki_page_html_row(page_id, Xodb_wiki_page_html_row.Tid_page, tmp_bfr.Xto_bry_and_clear()); } - public Hdump_text_row Make_row_img(Hdump_data_img__base... itms) { + public Xodb_wiki_page_html_row Make_row_img(Hdump_data_img__base... itms) { ListAdp tmp_list = ListAdp_.new_(); tmp_list.AddMany((Object[])itms); byte[] imgs_bry = Hdump_save_mgr.Write_imgs(tmp_bfr, tmp_list); - return new Hdump_text_row(page_id, Hdump_text_row_tid.Tid_data, imgs_bry); + return new Xodb_wiki_page_html_row(page_id, Xodb_wiki_page_html_row.Tid_data, imgs_bry); } - public Hdump_text_row Make_row_redlink(int... uids) { + public Xodb_wiki_page_html_row Make_row_redlink(int... uids) { Xopg_redlink_mgr redlink_mgr = new Xopg_redlink_mgr(); for (int uid : uids) redlink_mgr.Add(uid); byte[] redlinks_bry = Hdump_save_mgr.Write_redlinks(tmp_bfr, redlink_mgr); - return new Hdump_text_row(page_id, Hdump_data_tid.Tid_redlink, redlinks_bry); + return new Xodb_wiki_page_html_row(page_id, Hdump_data_tid.Tid_redlink, redlinks_bry); } @Override public void Exec_write(String raw) { super.Exec_write(raw); @@ -118,18 +118,18 @@ class Xodb_hdump_mgr__save_fxt extends Xodb_hdump_mgr__base_fxt { Hdump_page_body_srl.Save(tmp_bfr, page); Tfds.Eq(expd, tmp_bfr.Xto_str_and_clear()); } - public void Test_save(String raw, Hdump_text_row... expd) { + public void Test_save(String raw, Xodb_wiki_page_html_row... expd) { this.Exec_write(raw); hdump_mgr.Save_mgr().Update(page); hdump_mgr.Text_tbl().Select_by_page(expd_rows, 0); - Hdump_text_row[] actl = (Hdump_text_row[])expd_rows.Xto_ary_and_clear(Hdump_text_row.class); + Xodb_wiki_page_html_row[] actl = (Xodb_wiki_page_html_row[])expd_rows.Xto_ary_and_clear(Xodb_wiki_page_html_row.class); Tfds.Eq_ary_str(Xto_str_ary(tmp_bfr, expd), Xto_str_ary(tmp_bfr, actl)); } - private static String[] Xto_str_ary(Bry_bfr bfr, Hdump_text_row[] ary) { + private static String[] Xto_str_ary(Bry_bfr bfr, Xodb_wiki_page_html_row[] ary) { int len = ary.length; String[] rv = new String[len]; for (int i = 0; i < len; ++i) { - Hdump_text_row itm = ary[i]; + Xodb_wiki_page_html_row itm = ary[i]; bfr .Add_int_variable(itm.Page_id()) .Add_byte_pipe().Add_int_variable(itm.Tid()) .Add_byte_pipe().Add(itm.Data()) @@ -146,5 +146,5 @@ class Hdump_text_row_img { public int Img_h() {return img_h;} private int img_h; public byte[] Lnki_ttl() {return lnki_ttl;} private byte[] lnki_ttl; public byte[] Img_src_rel() {return img_src_rel;} private byte[] img_src_rel; - // return new Hdump_text_row(page_id, Hdump_text_row_tid.Tid_img, 0, Hdump_save_mgr.Write_img(bfr, uid, img_w, img_h, Bry_.new_utf8_(lnki_ttl), Bry_.new_utf8_(img_src_rel))) + // return new Xodb_wiki_page_html_row(page_id, Xodb_wiki_page_html_row.Tid_img, 0, Hdump_save_mgr.Write_img(bfr, uid, img_w, img_h, Bry_.new_utf8_(lnki_ttl), Bry_.new_utf8_(img_src_rel))) } diff --git a/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr_setup.java b/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr_setup.java index ab90fa432..5ac0df465 100644 --- a/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr_setup.java +++ b/400_xowa/src/gplx/xowa/hdumps/Xodb_hdump_mgr_setup.java @@ -39,16 +39,17 @@ public class Xodb_hdump_mgr_setup { try { core_provider.Exec_sql(Sql_ddl__page_html_db_id); cfg_tbl.Insert_str(Xodb_fsys_mgr.Cfg_grp_db_meta, Cfg_itm_html_db_exists, "y"); + cfg_tbl.Provider().Txn_mgr().Txn_end_all_bgn_if_none(); } catch (Exception e) {Gfo_usr_dlg_._.Warn_many("", "", "failed to update core: db=~{0} err=~{1}", core_provider.Conn_info().Str_raw(), Err_.Message_gplx(e));} } private static Xodb_file Create_db(Xodb_mgr_sql db_mgr, Xodb_fsys_mgr fsys_mgr) { Xodb_file html_db_file = fsys_mgr.Make(Xodb_file_tid.Tid_html); - html_db_file.Provider().Exec_sql(Hdump_text_tbl.Tbl_sql); + html_db_file.Provider().Exec_sql(Xodb_wiki_page_html_tbl.Tbl_sql); db_mgr.Tbl_xowa_db().Commit_all(fsys_mgr.Provider_core(), db_mgr.Fsys_mgr().Files_ary()); return html_db_file; } private static void Create_idx(Xodb_file html_db_file) { - Sqlite_engine_.Idx_create(html_db_file.Provider(), Hdump_text_tbl.Idx_core); + Sqlite_engine_.Idx_create(html_db_file.Provider(), Xodb_wiki_page_html_tbl.Idx_core); } private static final String Cfg_itm_html_db_exists = "html_db.exists"; public static final String diff --git a/400_xowa/src/gplx/xowa/hdumps/Xodbv_page_tbl.java b/400_xowa/src/gplx/xowa/hdumps/Xodbv_page_tbl.java index 37431a9ed..5966c3322 100644 --- a/400_xowa/src/gplx/xowa/hdumps/Xodbv_page_tbl.java +++ b/400_xowa/src/gplx/xowa/hdumps/Xodbv_page_tbl.java @@ -22,8 +22,8 @@ public class Xodbv_page_tbl { , Fld_page_id = "page_id", Fld_page_ns = "page_namespace", Fld_page_title = "page_title" , Fld_page_is_redirect = "page_is_redirect", Fld_page_touched = "page_touched", Fld_page_len = "page_len" , Fld_page_random_int = "page_random_int", Fld_page_file_idx = "page_file_idx" - , Fld_page_html_db_id = "page_html_db_id"; - private static final String[] Select_by_id_flds__hdump = new String[] {Fld_page_id, Fld_page_ns, Fld_page_title, Fld_page_touched, Fld_page_is_redirect, Fld_page_len, Fld_page_file_idx, Fld_page_html_db_id}; + , Fld_page_html_db_id = "page_html_db_id", Fld_page_redirect_id = "page_redirect_id"; + private static final String[] Select_by_id_flds__hdump = new String[] {Fld_page_id, Fld_page_ns, Fld_page_title, Fld_page_touched, Fld_page_is_redirect, Fld_page_len, Fld_page_file_idx, Fld_page_html_db_id, Fld_page_redirect_id}; public boolean Select_by_ttl(Xodb_page rv, Db_provider provider, Xow_ns ns, byte[] ttl) { Db_rdr rdr = Db_rdr_.Null; Db_stmt stmt = Db_stmt_.Null; try { @@ -36,6 +36,18 @@ public class Xodbv_page_tbl { } finally {rdr.Close(); stmt.Rls();} return false; } + public boolean Select_by_id(Xodb_page rv, Db_provider provider, int page_id) { + Db_rdr rdr = Db_rdr_.Null; Db_stmt stmt = Db_stmt_.Null; + try { + stmt = Db_stmt_.new_select_as_rdr(provider, Db_qry__select_in_tbl.new_(Tbl_name, String_.Ary(Fld_page_id), Select_by_id_flds__hdump)); + rdr = stmt.Val_int_(page_id).Exec_select_as_rdr(); + if (rdr.Move_next()) { + Read_page__all(rv, rdr); + return true; + } + } finally {rdr.Close(); stmt.Rls();} + return false; + } public static void Read_page__all(Xodb_page page, Db_rdr rdr) { page.Id_ (rdr.Read_int(0)); page.Ns_id_ (rdr.Read_int(1)); @@ -45,6 +57,7 @@ public class Xodbv_page_tbl { page.Text_len_ (rdr.Read_int(5)); page.Text_db_id_ (rdr.Read_int(6)); page.Html_db_id_ (rdr.Read_int(7)); + page.Redirect_id_ (rdr.Read_int(8)); } private static final String Page_touched_fmt = "yyyyMMddHHmmss"; } diff --git a/400_xowa/src/gplx/xowa/hdumps/Xowd_hdump_mgr.java b/400_xowa/src/gplx/xowa/hdumps/Xowd_hdump_mgr.java index 877b04114..149c6f48a 100644 --- a/400_xowa/src/gplx/xowa/hdumps/Xowd_hdump_mgr.java +++ b/400_xowa/src/gplx/xowa/hdumps/Xowd_hdump_mgr.java @@ -30,10 +30,19 @@ public class Xowd_hdump_mgr { public void Load(Hdump_page rv, byte[] ttl_bry) { Xoa_ttl ttl = wiki.Ttl_parse(ttl_bry); wiki_db_mgr.Tbl_mgr().Tbl__page().Select_by_ttl(dbpg, app.Db_mgr().Get(wiki_db_mgr.Key__core()), ttl.Ns(), ttl.Page_db()); + if (dbpg.Redirect_id() != -1) Select_by_id(rv, dbpg); if (dbpg.Html_db_id() == -1) return; // should return "not found" message load_mgr.Load2(rv, app.Db_mgr().Get(wiki_db_mgr.Key_by_idx(dbpg.Html_db_id())), dbpg.Id(), ttl); Bry_bfr bfr = app.Utl_bfr_mkr().Get_m001(); html_body.Init_by_page(wiki.Domain_bry(), rv).Write(bfr); rv.Page_body_(bfr.Mkr_rls().Xto_bry_and_clear()); } + private void Select_by_id(Hdump_page hpg, Xodb_page dbpg) { + int redirect_count = 0; + while (redirect_count < 5) { + int redirect_id = dbpg.Redirect_id(); + wiki_db_mgr.Tbl_mgr().Tbl__page().Select_by_id(dbpg, app.Db_mgr().Get(wiki_db_mgr.Key__core()), redirect_id); + if (redirect_id == -1) break; + } + } } diff --git a/400_xowa/src/gplx/xowa/hdumps/core/Hdump_img_bldr.java b/400_xowa/src/gplx/xowa/hdumps/core/Hdump_img_bldr.java index e1830573a..16ce7e1f5 100644 --- a/400_xowa/src/gplx/xowa/hdumps/core/Hdump_img_bldr.java +++ b/400_xowa/src/gplx/xowa/hdumps/core/Hdump_img_bldr.java @@ -18,7 +18,7 @@ along with this program. If not, see . package gplx.xowa.hdumps.core; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; import gplx.dbs.*; import gplx.xowa.hdumps.dbs.*; import gplx.xowa.bldrs.*; import gplx.xowa.bldrs.oimgs.*; class Hdump_img_bldr_cmd extends Xob_itm_basic_base implements Xob_cmd { - private Hdump_text_tbl text_tbl = new Hdump_text_tbl(); + private Xodb_wiki_page_html_tbl text_tbl = new Xodb_wiki_page_html_tbl(); public Hdump_img_bldr_cmd(Xob_bldr bldr, Xow_wiki wiki) {this.Cmd_ctor(bldr, wiki);} public String Cmd_key() {return Key_const;} public static final String Key_const = "hdump.make.imgs"; public void Cmd_ini(Xob_bldr bldr) {} diff --git a/400_xowa/src/gplx/xowa/hdumps/core/Hdump_module_mgr.java b/400_xowa/src/gplx/xowa/hdumps/core/Hdump_module_mgr.java index fef97a5aa..f38f7cceb 100644 --- a/400_xowa/src/gplx/xowa/hdumps/core/Hdump_module_mgr.java +++ b/400_xowa/src/gplx/xowa/hdumps/core/Hdump_module_mgr.java @@ -21,6 +21,12 @@ public class Hdump_module_mgr { public boolean Imap_exists() {return imap_exists;} public void Imap_exists_(boolean v) {imap_exists = v;} private boolean imap_exists; public boolean Gallery_packed_exists() {return gallery_packed_exists;} public void Gallery_packed_exists_(boolean v) {gallery_packed_exists = v;} private boolean gallery_packed_exists; public boolean Hiero_exists() {return hiero_exists;} public void Hiero_exists_(boolean v) {hiero_exists = v;} private boolean hiero_exists; + public void Init(boolean math, boolean imap, boolean packed, boolean hiero) { + this.math_exists = math; + this.imap_exists = imap; + this.gallery_packed_exists = packed; + this.hiero_exists = hiero; + } public void Clear() { math_exists = imap_exists = gallery_packed_exists = hiero_exists = false; } diff --git a/400_xowa/src/gplx/xowa/hdumps/core/Hdump_page.java b/400_xowa/src/gplx/xowa/hdumps/core/Hdump_page.java index fa3caced0..8d4e03212 100644 --- a/400_xowa/src/gplx/xowa/hdumps/core/Hdump_page.java +++ b/400_xowa/src/gplx/xowa/hdumps/core/Hdump_page.java @@ -16,6 +16,7 @@ You should have received a copy of the GNU Affero General Public License along with this program. If not, see . */ package gplx.xowa.hdumps.core; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; +import gplx.xowa.pages.*; import gplx.xowa.pages.skins.*; public class Hdump_page { public int Page_id() {return page_id;} private int page_id; public Xoa_url Page_url() {return page_url;} private Xoa_url page_url; @@ -39,4 +40,27 @@ public class Hdump_page { gly_itms.Clear(); return this; } + public void Init(Bry_bfr tmp_bfr, Xoa_page page) { + page_id = page.Revision_data().Id(); + page_body = page.Hdump_data().Body(); + Xopg_html_data html_data = page.Html_data(); + gplx.xowa.html.modules.Xoh_module_mgr mod_mgr = html_data.Module_mgr(); + module_mgr.Init(mod_mgr.Itm_mathjax().Enabled(), mod_mgr.Itm_popups().Bind_hover_area(), mod_mgr.Itm_gallery().Enabled(), mod_mgr.Itm_hiero().Enabled()); + display_ttl = html_data.Display_ttl(); + content_sub = html_data.Content_sub(); + sidebar_div = Save_sidebars(tmp_bfr, page, html_data); + } + private static byte[] Save_sidebars(Bry_bfr tmp_bfr, Xoa_page page, Xopg_html_data html_data) { + Xopg_xtn_skin_mgr mgr = html_data.Xtn_skin_mgr(); + int len = mgr.Count(); + boolean sidebar_exists = false; + for (int i = 0; i < len; ++i) { + Xopg_xtn_skin_itm itm = mgr.Get_at(i); + if (itm.Tid() == Xopg_xtn_skin_itm_tid.Tid_sidebar) { + sidebar_exists = true; + itm.Write(tmp_bfr, page); + } + } + return sidebar_exists ? tmp_bfr.Xto_bry_and_clear() : null; + } } diff --git a/400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_row.java b/400_xowa/src/gplx/xowa/hdumps/dbs/Xodb_wiki_page_html_row.java similarity index 65% rename from 400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_row.java rename to 400_xowa/src/gplx/xowa/hdumps/dbs/Xodb_wiki_page_html_row.java index c6008400d..3b3f41ad5 100644 --- a/400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_row.java +++ b/400_xowa/src/gplx/xowa/hdumps/dbs/Xodb_wiki_page_html_row.java @@ -16,9 +16,10 @@ You should have received a copy of the GNU Affero General Public License along with this program. If not, see . */ package gplx.xowa.hdumps.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; -public class Hdump_text_row { - public Hdump_text_row(int page_id, int tid, byte[] data) {this.page_id = page_id; this.tid = tid; this.data = data;} - public int Page_id() {return page_id;} private int page_id; - public int Tid() {return tid;} private int tid; - public byte[] Data() {return data;} private byte[] data; +public class Xodb_wiki_page_html_row { + public Xodb_wiki_page_html_row(int page_id, int tid, byte[] data) {this.page_id = page_id; this.tid = tid; this.data = data;} + public int Page_id() {return page_id;} private final int page_id; + public int Tid() {return tid;} private final int tid; + public byte[] Data() {return data;} private final byte[] data; + public static final int Tid_page = 0, Tid_data = 1; // SERIALIZED } diff --git a/400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_tbl.java b/400_xowa/src/gplx/xowa/hdumps/dbs/Xodb_wiki_page_html_tbl.java similarity index 61% rename from 400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_tbl.java rename to 400_xowa/src/gplx/xowa/hdumps/dbs/Xodb_wiki_page_html_tbl.java index 9e711baf3..4768262d8 100644 --- a/400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_tbl.java +++ b/400_xowa/src/gplx/xowa/hdumps/dbs/Xodb_wiki_page_html_tbl.java @@ -17,45 +17,43 @@ along with this program. If not, see . */ package gplx.xowa.hdumps.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; import gplx.ios.*; import gplx.dbs.*; import gplx.xowa.dbs.*; -public class Hdump_text_tbl { - public static final String Tbl_name = "html_text", Fld_page_id = "page_id", Fld_text_tid = "text_tid", Fld_text_data = "text_data"; - private Xodb_mgr db_mgr; private Io_stream_zip_mgr zip_mgr; +public class Xodb_wiki_page_html_tbl { + private Io_stream_zip_mgr zip_mgr = new Io_stream_zip_mgr(); private Db_stmt stmt_select, stmt_insert, stmt_delete; - public void Init_by_wiki(Xow_wiki wiki) {this.db_mgr = wiki.Db_mgr(); this.zip_mgr = wiki.App().Zip_mgr();} - public Db_provider Provider() {return provider;} public Hdump_text_tbl Provider_(Db_provider v) {this.Rls_all(); provider = v; return this;} private Db_provider provider; - @gplx.Virtual public void Delete_by_page(int page_id) { - if (stmt_delete == null) stmt_delete = Db_stmt_.new_delete_(provider, Tbl_name, Fld_page_id); - try {stmt_delete.Clear().Val_int_(page_id).Exec_delete();} - catch (Exception exc) {stmt_delete = null; throw Err_.err_(exc, "stmt failed");} // must reset stmt, else next call will fail + public void Init_by_wiki(Xow_wiki wiki) { + this.zip_mgr = wiki.App().Zip_mgr(); } + public byte Zip_tid() {return zip_tid;} public void Zip_tid_(byte v) {zip_tid = v;} private byte zip_tid = Io_stream_.Tid_gzip; + public Db_provider Provider() {return provider;} public Xodb_wiki_page_html_tbl Provider_(Db_provider v) {this.Rls_all(); provider = v; return this;} private Db_provider provider; @gplx.Virtual public int Insert(int page_id, int tid, byte[] data) { - if (stmt_insert == null) stmt_insert = Db_stmt_.new_insert_(provider, Tbl_name, Flds_all); - if (zip_mgr != null) data = zip_mgr.Zip(db_mgr.Data_storage_format(), data); + if (stmt_insert == null) stmt_insert = Db_stmt_.new_insert_(provider, Tbl_name, Flds__all); try { - stmt_insert.Clear().Val_int_(page_id).Val_int_(tid).Val_str_by_bry_(data).Exec_insert(); + data = zip_mgr.Zip(zip_tid, data); + stmt_insert.Clear().Val_int_(page_id).Val_int_(tid).Val_bry_(data).Exec_insert(); return data.length; } catch (Exception exc) {stmt_insert = null; throw Err_.err_(exc, "stmt failed");} // must reset stmt, else next call will fail } - private static final String[] Select_by_page_flds = new String[] {Fld_page_id, Fld_text_tid, Fld_text_data}; + @gplx.Virtual public void Delete(int page_id) { + if (stmt_delete == null) stmt_delete = Db_stmt_.new_delete_(provider, Tbl_name, Fld_page_id); + try {stmt_delete.Clear().Val_int_(page_id).Exec_delete();} + catch (Exception exc) {stmt_delete = null; throw Err_.err_(exc, "stmt failed");} // must reset stmt, else next call will fail + } @gplx.Virtual public void Select_by_page(ListAdp rv, int page_id) { - if (stmt_select == null) stmt_select = Db_stmt_.new_select_as_rdr(provider, Db_qry__select_in_tbl.new_(Tbl_name, String_.Ary(Fld_page_id), Select_by_page_flds)); + if (stmt_select == null) stmt_select = Db_stmt_.new_select_as_rdr(provider, Db_qry__select_in_tbl.new_(Tbl_name, String_.Ary(Fld_page_id), Flds__all)); try { Db_rdr rdr = stmt_select.Clear().Val_int_(page_id).Exec_select_as_rdr(); - while(rdr.Move_next()) { - byte[] data = rdr.Read_bry(2); - if (zip_mgr != null) data = zip_mgr.Unzip(db_mgr.Data_storage_format(), data); - Hdump_text_row row = new Hdump_text_row + while (rdr.Move_next()) { + Xodb_wiki_page_html_row row = new Xodb_wiki_page_html_row ( rdr.Read_int(0) , rdr.Read_int(1) - , data + , zip_mgr.Unzip(zip_tid, rdr.Read_bry(2)) ); rv.Add(row); } rdr.Close(); } catch (Exception exc) {stmt_select = null; throw Err_.err_(exc, "stmt failed");} // must reset stmt, else next call will fail - finally {if (stmt_select != null) stmt_select.Rls();} } public void Rls_all() { if (stmt_select != null) {stmt_select.Rls(); stmt_select = null;} @@ -63,15 +61,16 @@ public class Hdump_text_tbl { if (stmt_delete != null) {stmt_delete.Rls(); stmt_delete = null;} provider = null; } - private static final String[] Flds_all = new String[] {Fld_page_id, Fld_text_tid, Fld_text_data}; + public static final String Tbl_name = "wiki_page_html", Fld_page_id = "page_id", Fld_html_tid = "html_tid", Fld_html_data = "html_data"; + private static final String[] Flds__all = new String[] {Fld_page_id, Fld_html_tid, Fld_html_data}; public static final String Tbl_sql = String_.Concat_lines_nl - ( "CREATE TABLE IF NOT EXISTS html_text" + ( "CREATE TABLE IF NOT EXISTS wiki_page_html" , "( page_id integer NOT NULL" - , ", text_tid integer NOT NULL" - , ", text_data mediumblob NOT NULL" + , ", html_tid integer NOT NULL" + , ", html_data blob NOT NULL" , ");" ); public static final Db_idx_itm - Idx_core = Db_idx_itm.sql_("CREATE UNIQUE INDEX IF NOT EXISTS html_text__core ON html_text (page_id, text_tid);") + Idx_core = Db_idx_itm.sql_("CREATE UNIQUE INDEX IF NOT EXISTS wiki_page_html__core ON wiki_page_html (page_id, html_tid);") ; } diff --git a/400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_tbl_mem.java b/400_xowa/src/gplx/xowa/hdumps/dbs/Xodb_wiki_page_html_tbl_mem.java similarity index 79% rename from 400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_tbl_mem.java rename to 400_xowa/src/gplx/xowa/hdumps/dbs/Xodb_wiki_page_html_tbl_mem.java index 89b4a9e50..a9ab0a3b2 100644 --- a/400_xowa/src/gplx/xowa/hdumps/dbs/Hdump_text_tbl_mem.java +++ b/400_xowa/src/gplx/xowa/hdumps/dbs/Xodb_wiki_page_html_tbl_mem.java @@ -17,9 +17,9 @@ along with this program. If not, see . */ package gplx.xowa.hdumps.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; import gplx.dbs.*; -public class Hdump_text_tbl_mem extends Hdump_text_tbl { private HashAdp pages = HashAdp_.new_(); +public class Xodb_wiki_page_html_tbl_mem extends Xodb_wiki_page_html_tbl { private HashAdp pages = HashAdp_.new_(); @Override public int Insert(int page_id, int tid, byte[] data) { - Hdump_text_row row = new Hdump_text_row(page_id, tid, data); + Xodb_wiki_page_html_row row = new Xodb_wiki_page_html_row(page_id, tid, data); ListAdp rows = Get_or_new(pages, page_id); rows.Add(row); return data.length; @@ -28,11 +28,11 @@ public class Hdump_text_tbl_mem extends Hdump_text_tbl { private HashAdp pages ListAdp rows = Get_or_new(pages, page_id); int len = rows.Count(); for (int i = 0; i < len; ++i) { - Hdump_text_row row = (Hdump_text_row)rows.FetchAt(i); + Xodb_wiki_page_html_row row = (Xodb_wiki_page_html_row)rows.FetchAt(i); rv.Add(row); } } - @Override public void Delete_by_page(int page_id) {pages.Del(page_id);} + @Override public void Delete(int page_id) {pages.Del(page_id);} private static ListAdp Get_or_new(HashAdp pages, int page_id) { ListAdp rv = (ListAdp)pages.Fetch(page_id); if (rv == null) { diff --git a/400_xowa/src/gplx/xowa/hdumps/htmls/Hdump_html_consts.java b/400_xowa/src/gplx/xowa/hdumps/htmls/Hdump_html_consts.java index a2a982096..6008353c9 100644 --- a/400_xowa/src/gplx/xowa/hdumps/htmls/Hdump_html_consts.java +++ b/400_xowa/src/gplx/xowa/hdumps/htmls/Hdump_html_consts.java @@ -26,7 +26,7 @@ public class Hdump_html_consts { public static final byte Tid_dir = 1, Tid_img = 2, Tid_img_style = 3, Tid_file_play = 4, Tid_file_info = 5, Tid_file_mgnf = 6 , Tid_hiero_dir = 7, Tid_gallery_box_max = 8, Tid_gallery_box_w = 9, Tid_gallery_img_w = 10, Tid_gallery_img_pad = 11 - , Tid_redlink = 12 + , Tid_redlink = 12, Tid_toc = 13 ; public static final byte[] Key_dir = Bry_.new_ascii_("~{xowa_dir}") @@ -41,6 +41,7 @@ public class Hdump_html_consts { , Key_gallery_img_w = Bry_.new_ascii_("xowa_gly_img_w='") , Key_gallery_img_pad = Bry_.new_ascii_("xowa_gly_img_pad='") , Key_redlink = Bry_.new_ascii_("xowa_redlink='") + , Key_toc = Bry_.new_ascii_("~{xowa_toc}") ; public static final byte[] Html_redlink_bgn = Bry_.Add(Bry_.new_ascii_("\" "), Key_redlink) @@ -60,6 +61,7 @@ public class Hdump_html_consts { trie_itm(rv, Tid_gallery_img_w , Byte_ascii.Apos , Key_gallery_img_w); trie_itm(rv, Tid_gallery_img_pad , Byte_ascii.Apos , Key_gallery_img_pad); trie_itm(rv, Tid_redlink , Byte_ascii.Apos , Key_redlink); + trie_itm(rv, Tid_toc , Byte_ascii.Nil , Key_toc); return rv; } private static void trie_itm(Btrie_slim_mgr trie, byte tid, byte subst_end_byte, byte[] key_bry) { diff --git a/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_dict.java b/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_dict.java new file mode 100644 index 000000000..13265eebc --- /dev/null +++ b/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_dict.java @@ -0,0 +1,34 @@ +/* +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 . +*/ +package gplx.xowa.hdumps.hzips; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; +class Xoa_hzip_dict {// SERIALIZED + public static final byte Escape = Byte_.int_(255); + public static final byte[] Escape_bry = Bry_.ints_(255); + public static final byte + Tid_a_end = 0 + , Tid_lnki_ttl = 1 + , Tid_lnki_capt = 2 + , Tid_lnke = 3 // blog -> 255,4,h,xowa.sourceforge/blog.html,255,blog,255,0 + ; + public static final byte[] + Bry_a_end = Bry_.ints_(Escape, Tid_a_end) + , Bry_lnki_ttl = Bry_.ints_(Escape, Tid_lnki_ttl) + , Bry_lnki_capt = Bry_.ints_(Escape, Tid_lnki_capt) + , Bry_lnke = Bry_.ints_(Escape, Tid_lnke) // blog -> 255,4,h,xowa.sourceforge/blog.html,255,blog,255,0 + ; +} diff --git a/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_itm__lnki.java b/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_itm__lnki.java new file mode 100644 index 000000000..82576d7c5 --- /dev/null +++ b/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_itm__lnki.java @@ -0,0 +1,110 @@ +/* +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 . +*/ +package gplx.xowa.hdumps.hzips; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; +import gplx.html.*; +public class Xoa_hzip_itm__lnki { + private Xoa_hzip_mgr hzip_mgr; private Xow_wiki wiki; + public Xoa_hzip_itm__lnki(Xoa_hzip_mgr hzip_mgr, Xow_wiki wiki) {this.hzip_mgr = hzip_mgr; this.wiki = wiki;} + public int Save(Bry_bfr bfr, byte[] src, int src_len, int bgn, int pos) { + int xtid_bgn = pos + Find_xtid_len; if (!Bry_.Match(src, pos, xtid_bgn, Find_xtid_bry)) return Xoa_hzip_mgr.Unhandled; // next atr should be "xtid='" + int xtid_end = Bry_finder.Find_fwd(src, Byte_ascii.Apos, xtid_bgn); if (xtid_end == Bry_finder.Not_found) return hzip_mgr.Warn_by_pos_add_dflt("a.xtid_end_missing", bgn, xtid_bgn); + Object xtid_obj = Xtids.Get_by_mid(src, xtid_bgn, xtid_end); if (xtid_obj == null) return hzip_mgr.Warn_by_pos("a.xtid_invalid", xtid_bgn, xtid_end); + byte xtid = ((Byte_obj_val)xtid_obj).Val(); + switch (xtid) { + case Xtid_ttl_int: return Save_basic(bfr, src, src_len, bgn, xtid_end, Bool_.N); + case Xtid_capt_int: return Save_basic(bfr, src, src_len, bgn, xtid_end, Bool_.Y); + default: return hzip_mgr.Warn_by_pos("a.xtid_unknown", xtid_bgn, xtid_end); + } + } + private int Save_basic(Bry_bfr bfr, byte[] src, int src_len, int bgn, int pos, boolean caption) { + int ttl_bgn = Bry_finder.Find_fwd(src, Find_href_bry, pos, src_len); if (ttl_bgn == Bry_finder.Not_found) return Xoa_hzip_mgr.Unhandled;//hzip_mgr.Warn_by_pos_add_dflt("a.ttl_bgn_missing", bgn, pos); + ttl_bgn += Find_href_len; + int ttl_end = Bry_finder.Find_fwd(src, Byte_ascii.Quote, ttl_bgn , src_len); if (ttl_end == Bry_finder.Not_found) return hzip_mgr.Warn_by_pos_add_dflt("a.ttl_end_missing", bgn, ttl_bgn); + Xoa_ttl ttl = Xoa_ttl.parse_(wiki, Bry_.Mid(src, ttl_bgn, ttl_end)); if (ttl == null) return hzip_mgr.Warn_by_pos("a.ttl_invalid", ttl_bgn, ttl_end); + int a_lhs_end = Bry_finder.Find_fwd(src, Byte_ascii.Gt, ttl_end, src_len); if (a_lhs_end == Bry_finder.Not_found) return hzip_mgr.Warn_by_pos_add_dflt("a.a_lhs_end_missing", bgn, ttl_end); + ++a_lhs_end; // skip > + int a_rhs_bgn = Bry_finder.Find_fwd(src, Find_a_rhs_bgn_bry, a_lhs_end, src_len); if (a_rhs_bgn == Bry_finder.Not_found) return hzip_mgr.Warn_by_pos_add_dflt("a.a_rhs_bgn_missing", bgn, ttl_end); + if (caption) + bfr.Add(Xoa_hzip_dict.Bry_lnki_capt); + else + bfr.Add(Xoa_hzip_dict.Bry_lnki_ttl); + bfr.Add_byte((byte)ttl.Ns().Ord()); // ASSUME:NS_MAX_255 + if (caption) + bfr.Add(ttl.Page_db()); + else { + int capt_len = a_rhs_bgn - a_lhs_end; + int ttl_len = ttl_end - ttl_bgn; + if (capt_len == ttl_len && Bry_.Match(src, ttl_bgn, ttl_end, src, a_lhs_end, a_rhs_bgn)) + bfr.Add(ttl.Page_db()); + else + bfr.Add_mid(src, a_lhs_end, a_rhs_bgn); + } + bfr.Add_byte(Xoa_hzip_dict.Escape); + if (caption) { + bfr.Add_mid(src, a_lhs_end, a_rhs_bgn); + bfr.Add(Xoa_hzip_dict.Bry_a_end); + } + return a_rhs_bgn + Find_a_rhs_bgn_len; + } + public int Load_ttl(Bry_bfr bfr, byte[] src, int src_len, int bgn, byte tid) { + byte ns_ord = src[bgn]; + Xow_ns ns = wiki.Ns_mgr().Ords_get_at(ns_ord); + int ttl_bgn = bgn + 1; + int ttl_end = Bry_finder.Find_fwd(src, Xoa_hzip_dict.Escape, ttl_bgn, src_len); if (ttl_end == Bry_finder.Not_found) return hzip_mgr.Warn_by_pos_add_dflt("a.ttl_end_missing", bgn, ttl_bgn); + byte[] ttl_bry = Bry_.Mid(src, ttl_bgn, ttl_end); + Xoa_ttl ttl = Xoa_ttl.parse_(wiki, ns.Id(), ttl_bry); + bfr.Add_str("").Add(ttl_bry); + } + else { + int capt_end = Bry_finder.Find_fwd(src, Xoa_hzip_dict.Bry_a_end, rv, src_len); if (capt_end == Bry_finder.Not_found) return hzip_mgr.Warn_by_pos_add_dflt("a.capt_end_missing", bgn, rv); + ttl_bry = Bry_.Mid(src, rv, capt_end); + bfr.Add(Html_utl.Escape_html_as_bry(ttl_bry)).Add_str("'>").Add(ttl_bry); + rv = capt_end + Xoa_hzip_dict.Bry_a_end.length; + } + bfr.Add_str(""); + return rv; + } + public void Html(Bry_bfr bfr, boolean caption) {bfr.Add(caption ? Html_capt : Html_ttl);} + private static final byte[] Html_ttl = Bry_.new_ascii_("") + ; + private static final int + Find_xtid_len = Find_xtid_bry.length + , Find_href_len = Find_href_bry.length + , Find_a_rhs_bgn_len = Find_a_rhs_bgn_bry.length + ; + private static final byte[] + Xtid_ttl_bry = Bry_.new_ascii_("a_ttl") + , Xtid_capt_bry = Bry_.new_ascii_("a_capt") + ; + private static final byte + Xtid_ttl_int = 0 + , Xtid_capt_int = 1 + ; + private static final Hash_adp_bry Xtids = Hash_adp_bry.cs_() + .Add_bry_byte(Xtid_ttl_bry , Xtid_ttl_int) + .Add_bry_byte(Xtid_capt_bry , Xtid_capt_int) + ; +} diff --git a/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_itm__lnki_tst.java b/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_itm__lnki_tst.java new file mode 100644 index 000000000..2bc801bc5 --- /dev/null +++ b/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_itm__lnki_tst.java @@ -0,0 +1,118 @@ +/* +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 . +*/ +package gplx.xowa.hdumps.hzips; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; +import org.junit.*; import gplx.xowa.html.*; +public class Xoa_hzip_itm__lnki_tst { + @Before public void init() {fxt.Clear();} private Xoa_hzip_itm__lnki_fxt fxt = new Xoa_hzip_itm__lnki_fxt(); + @Test public void Srl_ttl() { + byte[][] brys = Bry_.Ary(Xoa_hzip_dict.Bry_lnki_ttl, Bry_.ints_(2), Bry_.new_ascii_("A"), Xoa_hzip_dict.Escape_bry); + fxt.Test_save(brys, "A"); + fxt.Test_load(brys, "A"); + } + @Test public void Srl_ttl_alt_case() { + byte[][] brys = Bry_.Ary(Xoa_hzip_dict.Bry_lnki_ttl, Bry_.ints_(2), Bry_.new_ascii_("a"), Xoa_hzip_dict.Escape_bry); + fxt.Test_save(brys, "a"); + fxt.Test_load(brys, "a"); + } + @Test public void Srl_ttl_ns() { + byte[][] brys = Bry_.Ary(Xoa_hzip_dict.Bry_lnki_ttl, Bry_.ints_(12), Bry_.new_ascii_("A"), Xoa_hzip_dict.Escape_bry); + fxt.Test_save(brys, "Template:A"); + fxt.Test_load(brys, "Template:A"); + } + @Test public void Srl_ttl_smoke() { + byte[][] brys = Bry_.Ary(Bry_.new_ascii_("a_1"), Xoa_hzip_dict.Bry_lnki_ttl, Bry_.ints_(2), Bry_.new_ascii_("A"), Xoa_hzip_dict.Escape_bry, Bry_.new_ascii_("a_2")); + fxt.Test_save(brys, "a_1Aa_2"); + fxt.Test_load(brys, "a_1Aa_2"); + } + @Test public void Srl_capt() { + byte[][] brys = Bry_.Ary(Xoa_hzip_dict.Bry_lnki_capt, Bry_.ints_(2), Bry_.new_ascii_("A"), Xoa_hzip_dict.Escape_bry, Bry_.new_ascii_("A1"), Xoa_hzip_dict.Bry_a_end); + fxt.Test_save(brys, "A1"); + fxt.Test_load(brys, "A1"); + } + @Test public void Srl_noop() { + fxt.Test_save("A", Bry_.new_utf8_("A")); + } + @Test public void Html_ttl() { + fxt.Test_html("[[A]]", "A"); + } + @Test public void Html_capt() { + fxt.Test_html("[[A|a]]", "a"); + } +} +class Xoa_hzip_itm__lnki_fxt { + private Bry_bfr bfr = Bry_bfr.reset_(Io_mgr.Len_mb); private Xoa_hzip_mgr hzip_mgr; private Xow_wiki wiki; + public void Clear() { + if (hzip_mgr == null) { + Xoa_app app = Xoa_app_fxt.app_(); + wiki = Xoa_app_fxt.wiki_tst_(app); + hzip_mgr = new Xoa_hzip_mgr(Gfo_usr_dlg_._, wiki); + } + } + public void Test_save(byte[][] expd_brys, String html) {Test_save(html, expd_brys);} + public void Test_save(String html, byte[]... expd_brys) { + byte[] expd = Bry_.Add(expd_brys); + hzip_mgr.Save(bfr, Bry_.Empty, Bry_.new_utf8_(html)); + Tfds.Eq_ary(expd, bfr.Xto_bry_and_clear()); + } + public void Test_load(byte[][] src_brys, String expd) { + byte[] src = Bry_.Add(src_brys); + hzip_mgr.Load(bfr, Bry_.Empty, src); + Tfds.Eq_ary(Bry_.new_utf8_(expd), bfr.Xto_bry_and_clear()); + } + public void Test_html(String html, String expd) { + Xop_ctx ctx = wiki.Ctx(); Xop_parser parser = wiki.Parser(); Xop_tkn_mkr tkn_mkr = ctx.Tkn_mkr(); + ctx.Para().Enabled_n_(); + ctx.Cur_page().Lnki_redlinks_mgr().Clear(); + byte[] html_bry = Bry_.new_utf8_(html); + Xop_root_tkn root = ctx.Tkn_mkr().Root(html_bry); + parser.Parse_page_all_clear(root, ctx, tkn_mkr, html_bry); + Xoh_wtr_ctx hctx = Xoh_wtr_ctx.Hdump; + Xoh_html_wtr html_wtr = wiki.Html_mgr().Html_wtr(); + html_wtr.Write_all(bfr, ctx, hctx, html_bry, root); + Tfds.Eq(expd, bfr.Xto_str_and_clear()); + } +} +class Xoa_hzip_itm__href { + // + // e // xwiki [[simple:xx + // "Descriptor Terms (Feature Types)" + // 255,5, + public static final byte + Tid_proto_none = 0 + , Tid_proto_http = 1 + , Tid_proto_https = 2 + , Tid_proto_other = 3 + ; + public static final byte + Tid_domain_com = 0 + , Tid_domain_org = 1 + , Tid_domain_net = 2 + , Tid_domain_gov = 3 + , Tid_domain_other = 4 + ; + public static final byte + Tid_ext_none = 0 + , Tid_ext_htm = 1 + , Tid_ext_html = 2 + , Tid_ext_php = 3 + , Tid_ext_jsp = 4 + , Tid_ext_asp = 5 + , Tid_ext_aspx = 6 + , Tid_ext_other = 7 + ; +} diff --git a/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_mgr.java b/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_mgr.java new file mode 100644 index 000000000..65ba9f205 --- /dev/null +++ b/400_xowa/src/gplx/xowa/hdumps/hzips/Xoa_hzip_mgr.java @@ -0,0 +1,93 @@ +/* +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 . +*/ +package gplx.xowa.hdumps.hzips; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; +import gplx.core.btries.*; +public class Xoa_hzip_mgr { + private Gfo_usr_dlg usr_dlg; + private byte[] page_url; private byte[] src; private int src_len; + public Xoa_hzip_mgr(Gfo_usr_dlg usr_dlg, Xow_wiki wiki) { + this.usr_dlg = usr_dlg; + itm__lnki = new Xoa_hzip_itm__lnki(this, wiki); + } + public Xoa_hzip_itm__lnki Itm__lnki() {return itm__lnki;} private Xoa_hzip_itm__lnki itm__lnki; + public void Save(Bry_bfr bfr, byte[] page_url, byte[] src) { + this.page_url = page_url; this.src = src; + this.src_len = src.length; + int pos = 0, add_bgn = -1; + bfr.Clear(); + while (pos < src_len) { + byte b = src[pos]; + Object o = save_trie.Match_bgn_w_byte(b, src, pos, src_len); + if (o == null) { + if (add_bgn == -1) add_bgn = pos; + ++pos; + } + else { + if (add_bgn != -1) {bfr.Add_mid(src, add_bgn, pos); add_bgn = -1;} + byte tid = ((Byte_obj_val)o).Val(); + int match_bgn = pos; + int match_end = save_trie.Match_pos(); + switch (tid) { + case Tid_a: pos = itm__lnki.Save(bfr, src, src_len, match_bgn, match_end); break; + default: Warn_by_pos("save.tid.unknown", match_bgn, match_end); pos = match_end; continue; + } + if (pos == Unhandled) { + bfr.Add_mid(src, match_bgn, match_end); + pos = match_end; + } + } + } + if (add_bgn != -1) bfr.Add_mid(src, add_bgn, src_len); + } + public void Load(Bry_bfr bfr, byte[] page_url, byte[] src) { + this.page_url = page_url; this.src = src; + this.src_len = src.length; + int pos = 0, add_bgn = -1; + bfr.Clear(); + while (pos < src_len) { + byte b = src[pos]; + if (b == Xoa_hzip_dict.Escape) { + if (add_bgn != -1) {bfr.Add_mid(src, add_bgn, pos); add_bgn = -1;} + int itm_pos = pos + 2; if (itm_pos >= src_len) {Warn_by_pos("load.eos", pos, itm_pos); break;} + int tid_pos = pos + 1; + byte tid = src[tid_pos]; + switch (tid) { + case Xoa_hzip_dict.Tid_lnki_ttl : + case Xoa_hzip_dict.Tid_lnki_capt: pos = itm__lnki.Load_ttl(bfr, src, src_len, itm_pos, tid); break; + } + } + else { + if (add_bgn == -1) add_bgn = pos; + ++pos; + } + } + if (add_bgn != -1) bfr.Add_mid(src, add_bgn, src_len); + } + public int Warn_by_pos_add_dflt(String err, int bgn, int end) {return Warn_by_pos(err, bgn, end, 32);} + public int Warn_by_pos(String err, int bgn, int end) {return Warn_by_pos(err, bgn, end, 0);} + private int Warn_by_pos(String err, int bgn, int end, int end_adj) { + end += end_adj; if (end > src_len) end = src_len; + usr_dlg.Warn_many("", "", "hzip failed: page=~{0} err=~{1} mid=~{2}", String_.new_utf8_(page_url), err, String_.new_utf8_(src, bgn, end)); + return bgn; + } + public static final int Unhandled = -1; + private static final byte Tid_a = 0; + private Btrie_slim_mgr save_trie = Btrie_slim_mgr.cs_() + .Add_str_byte(". */ package gplx.xowa.hdumps.loads; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; import gplx.core.brys.*; import gplx.core.btries.*; import gplx.dbs.*; import gplx.ios.*; -import gplx.xowa.dbs.*; import gplx.xowa.pages.*; import gplx.xowa.hdumps.core.*; import gplx.xowa.hdumps.dbs.*; import gplx.xowa.hdumps.pages.*; import gplx.xowa.pages.skins.*; +import gplx.xowa.dbs.*; import gplx.xowa.pages.*; import gplx.xowa.hdumps.core.*; import gplx.xowa.hdumps.dbs.*; import gplx.xowa.hdumps.pages.*; import gplx.xowa.pages.skins.*; import gplx.xowa.hdumps.srls.*; public class Hdump_load_mgr { - private Hdump_text_tbl text_tbl = new Hdump_text_tbl(); private Bry_rdr rdr = new Bry_rdr(); // private Io_stream_zip_mgr zip_mgr = new Io_stream_zip_mgr(); + private Xodb_wiki_page_html_tbl text_tbl = new Xodb_wiki_page_html_tbl(); private Bry_rdr rdr = new Bry_rdr(); private ListAdp tmp_rows = ListAdp_.new_(), img_itms = ListAdp_.new_(); public Hdump_load_mgr() {} - public byte Zip_tid() {return zip_tid;} public void Zip_tid_(byte v) {zip_tid = v;} private byte zip_tid = gplx.ios.Io_stream_.Tid_file; + public void Zip_tid_(byte v) {text_tbl.Zip_tid_(v);} public void Load2(Hdump_page hpg, Db_provider provider, int page_id, Xoa_ttl page_ttl) { text_tbl.Provider_(provider).Select_by_page(tmp_rows, page_id); Load_rows(hpg, page_id, Xoa_url.blank_(), page_ttl, tmp_rows); @@ -37,15 +37,15 @@ public class Hdump_load_mgr { img_itms.Clear(); int len = rows.Count(); for (int i = 0; i < len; ++i) { - Hdump_text_row row = (Hdump_text_row)rows.FetchAt(i); + Xodb_wiki_page_html_row row = (Xodb_wiki_page_html_row)rows.FetchAt(i); switch (row.Tid()) { - case Hdump_text_row_tid.Tid_body: Hdump_page_body_srl.Load(hpg, rdr, row.Data()); break; - case Hdump_text_row_tid.Tid_data: Load_data(hpg, row); break; + case Xodb_wiki_page_html_row.Tid_page: srl_mgr.Load(hpg, row.Data()); break; + case Xodb_wiki_page_html_row.Tid_data: Load_data(hpg, row); break; } } rows.Clear(); - } - public void Load_data(Hdump_page hpg, Hdump_text_row row) { + } private Hpg_srl_mgr srl_mgr = Hpg_srl_mgr._i_; + public void Load_data(Hdump_page hpg, Xodb_wiki_page_html_row row) { rdr.Src_(row.Data()); while (!rdr.Pos_is_eos()) { int tid = rdr.Read_int_to_pipe(); diff --git a/400_xowa/src/gplx/xowa/hdumps/loads/Hdump_load_mgr_tst.java b/400_xowa/src/gplx/xowa/hdumps/loads/Hdump_load_mgr_tst.java index 5187f49eb..ddc5b6b32 100644 --- a/400_xowa/src/gplx/xowa/hdumps/loads/Hdump_load_mgr_tst.java +++ b/400_xowa/src/gplx/xowa/hdumps/loads/Hdump_load_mgr_tst.java @@ -19,19 +19,19 @@ package gplx.xowa.hdumps.loads; import gplx.*; import gplx.xowa.*; import gplx.x import org.junit.*; import gplx.xowa.files.*; import gplx.xowa.hdumps.dbs.*; import gplx.xowa.hdumps.core.*; import gplx.xowa.hdumps.saves.*; import gplx.xowa.hdumps.pages.*; import gplx.xowa.dbs.*; public class Hdump_load_mgr_tst { @Before public void init() {fxt.Clear();} private Hdump_load_mgr_fxt fxt = new Hdump_load_mgr_fxt(); - @Test public void Body() { - fxt.Init_row_body("", null, null, null); - fxt.Expd_body(""); - fxt.Test_load(0); - } - @Test public void Body_all() { - fxt.Init_row_body("", "test_display_ttl", "test_content_sub", "test_sidebar_div"); - fxt.Expd_body(""); - fxt.Expd_display_ttl("test_display_ttl"); - fxt.Expd_content_sub("test_content_sub"); - fxt.Expd_sidebar_div("test_sidebar_div"); - fxt.Test_load(0); - } +// @Test public void Body() { +// fxt.Init_row_body("", null, null, null); +// fxt.Expd_body(""); +// fxt.Test_load(0); +// } +// @Test public void Body_all() { +// fxt.Init_row_body("", "test_display_ttl", "test_content_sub", "test_sidebar_div"); +// fxt.Expd_body(""); +// fxt.Expd_display_ttl("test_display_ttl"); +// fxt.Expd_content_sub("test_content_sub"); +// fxt.Expd_sidebar_div("test_sidebar_div"); +// fxt.Test_load(0); +// } @Test public void Img() { fxt.Init_row_img ( fxt.Make_img("A.png", 0, 220, 110) @@ -65,7 +65,7 @@ class Hdump_load_mgr_fxt { Bry_bfr bfr = Bry_bfr.new_(255); tmp_list.AddMany((Object[])itms); byte[] imgs_bry = Hdump_save_mgr.Write_imgs(bfr, tmp_list); - init_rows.Add(new Hdump_text_row(0, Hdump_text_row_tid.Tid_data, imgs_bry)); + init_rows.Add(new Xodb_wiki_page_html_row(0, Xodb_wiki_page_html_row.Tid_data, imgs_bry)); } public Hdump_load_mgr_fxt Init_row_body(String body, String display_ttl, String content_sub, String sidebar_div) { Bry_bfr tmp_bfr = Bry_bfr.reset_(255); @@ -77,10 +77,10 @@ class Hdump_load_mgr_fxt { if (sidebar_div != null) page.Html_data().Xtn_skin_mgr().Add(new Xopg_xtn_skin_itm_mock(Bry_.new_utf8_(sidebar_div))); page.Hdump_data().Body_(Bry_.new_utf8_(body)); Hdump_page_body_srl.Save(tmp_bfr, page); - init_rows.Add(new Hdump_text_row(page_id, Hdump_text_row_tid.Tid_body, tmp_bfr.Xto_bry_and_clear())); + init_rows.Add(new Xodb_wiki_page_html_row(page_id, Xodb_wiki_page_html_row.Tid_page, tmp_bfr.Xto_bry_and_clear())); return this; } - public Hdump_load_mgr_fxt Init_row_img (String data) {init_rows.Add(new Hdump_text_row(page_id, Hdump_text_row_tid.Tid_data, Bry_.new_utf8_(data))); return this;} + public Hdump_load_mgr_fxt Init_row_img (String data) {init_rows.Add(new Xodb_wiki_page_html_row(page_id, Xodb_wiki_page_html_row.Tid_data, Bry_.new_utf8_(data))); return this;} public Hdump_load_mgr_fxt Expd_body(String v) {this.expd_body = v; return this;} public Hdump_load_mgr_fxt Expd_display_ttl(String v) {this.expd_display_ttl = v; return this;} public Hdump_load_mgr_fxt Expd_content_sub(String v) {this.expd_content_sub = v; return this;} diff --git a/400_xowa/src/gplx/xowa/hdumps/loads/Hdump_page_body_srl.java b/400_xowa/src/gplx/xowa/hdumps/loads/Hdump_page_body_srl.java index 0116a383b..4fead4441 100644 --- a/400_xowa/src/gplx/xowa/hdumps/loads/Hdump_page_body_srl.java +++ b/400_xowa/src/gplx/xowa/hdumps/loads/Hdump_page_body_srl.java @@ -21,14 +21,14 @@ import gplx.xowa.html.modules.*; public class Hdump_page_body_srl { private static final Bry_bfr tmp_bfr = Bry_bfr.reset_(255); public static void Save(Bry_bfr bfr, Xoa_page page) { - bfr.Add_int_fixed(0, 1).Add_byte_pipe(); // version + bfr.Add_int_fixed(0, 1).Add_byte_pipe(); // version Xopg_hdump_data hdump_data = page.Hdump_data(); bfr.Add_int_variable(hdump_data.Data_count_imgs()); // imgs_count Xopg_html_data html_data = page.Html_data(); Save_html_modules(bfr, html_data); Save_data(bfr, Tid_display_ttl , html_data.Display_ttl()); Save_data(bfr, Tid_content_sub , html_data.Content_sub()); - Save_sidebars(bfr, page, html_data); + Save_sidebars(bfr, page , html_data); Save_data(bfr, Tid_body , hdump_data.Body()); } private static void Save_html_modules(Bry_bfr bfr, Xopg_html_data html_data) { @@ -106,7 +106,7 @@ public class Hdump_page_body_srl { hpg.Version_id_(rdr.Read_int_to_pipe()); hpg.Img_count_(rdr.Read_int_to_nl()); } - private static final int + private static final int // SERIALIZED Tid_html_module = 1 , Tid_display_ttl = 2 , Tid_content_sub = 3 diff --git a/400_xowa/src/gplx/xowa/hdumps/saves/Hdump_save_mgr.java b/400_xowa/src/gplx/xowa/hdumps/saves/Hdump_save_mgr.java index b0777eb05..9e89341f9 100644 --- a/400_xowa/src/gplx/xowa/hdumps/saves/Hdump_save_mgr.java +++ b/400_xowa/src/gplx/xowa/hdumps/saves/Hdump_save_mgr.java @@ -16,16 +16,17 @@ You should have received a copy of the GNU Affero General Public License along with this program. If not, see . */ package gplx.xowa.hdumps.saves; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; -import gplx.dbs.*; import gplx.xowa.files.*; import gplx.xowa.hdumps.dbs.*; +import gplx.dbs.*; import gplx.xowa.files.*; import gplx.xowa.hdumps.dbs.*; import gplx.xowa.hdumps.srls.*; import gplx.xowa.hdumps.core.*; import gplx.xowa.hdumps.pages.*; import gplx.xowa.pages.*; import gplx.xowa.pages.skins.*; import gplx.xowa.hdumps.loads.*; public class Hdump_save_mgr { - private Bry_bfr tmp_bfr = Bry_bfr.reset_(10 * Io_mgr.Len_mb); - public Hdump_text_tbl Tbl() {return text_tbl;} public void Tbl_(Hdump_text_tbl v) {text_tbl = v;} private Hdump_text_tbl text_tbl; + private Bry_bfr tmp_bfr = Bry_bfr.reset_(1 * Io_mgr.Len_mb); + public Xodb_wiki_page_html_tbl Tbl() {return text_tbl;} public void Tbl_(Xodb_wiki_page_html_tbl v) {text_tbl = v;} private Xodb_wiki_page_html_tbl text_tbl; public void Update(Xoa_page page) { int page_id = page.Revision_data().Id(); - text_tbl.Delete_by_page(page_id); + text_tbl.Delete(page_id); this.Insert(page); } + public void Hdump_stats_enable_y_(Db_provider p) {hdump_stats_tbl = new Hdump_stats_tbl().Provider_(p).Create_tbl();} private Hdump_stats_tbl hdump_stats_tbl; public void Insert(Xoa_page page) { int page_id = page.Revision_data().Id(); Insert_body(page, page_id); @@ -35,10 +36,13 @@ public class Hdump_save_mgr { if (imgs_bry != null) text_tbl.Insert(page_id, Hdump_data_tid.Tid_img, imgs_bry); } public int Insert_body(Xoa_page page, int page_id) { - Hdump_page_body_srl.Save(tmp_bfr, page); + hpg.Init(tmp_bfr, page); + srl_mgr.Save(hpg, tmp_bfr); byte[] body_bry = tmp_bfr.Xto_bry_and_clear(); - return text_tbl.Insert(page_id, Hdump_text_row_tid.Tid_body, body_bry); - } + int insert_len = text_tbl.Insert(page_id, Xodb_wiki_page_html_row.Tid_page, body_bry); + if (hdump_stats_tbl != null) hdump_stats_tbl.Insert(hpg, page.Root().Root_src().length, body_bry.length, insert_len); + return insert_len; + } private Hpg_srl_mgr srl_mgr = Hpg_srl_mgr._i_; private Hdump_page hpg = new Hdump_page(); public static byte[] Write_imgs(Bry_bfr bfr, ListAdp imgs) { int len = imgs.Count(); if (len == 0) return null; // no images; exit early, else will write blank String for (int i = 0; i < len; ++i) { @@ -56,3 +60,53 @@ public class Hdump_save_mgr { return bfr.Xto_bry_and_clear(); } } +class Hdump_stats_tbl { + private Db_stmt stmt_insert; + public Db_provider Provider() {return provider;} public Hdump_stats_tbl Provider_(Db_provider v) {this.Rls_all(); provider = v; return this;} private Db_provider provider; + public Hdump_stats_tbl Create_tbl() {Sqlite_engine_.Tbl_create_and_delete(provider, Tbl_name, Tbl_sql); return this;} + public void Insert(Hdump_page hpg, int wtxt_len, int row_orig_len, int row_zip_len) { + Hdump_module_mgr js_mgr = hpg.Module_mgr(); + Insert + ( hpg.Page_id(), wtxt_len, row_orig_len, row_zip_len + , Len_or_0(hpg.Page_body()), Len_or_0(hpg.Display_ttl()), Len_or_0(hpg.Content_sub()), Len_or_0(hpg.Sidebar_div()) + , js_mgr.Math_exists(), js_mgr.Imap_exists(), js_mgr.Gallery_packed_exists(), js_mgr.Hiero_exists() + ); + } + private int Len_or_0(byte[] bry) {return bry == null ? 0 : bry.length;} + public void Insert(int page_id, int wtxt_len, int row_orig_len, int row_zip_len, int body_len, int display_ttl_len, int content_sub_len, int sidebar_div_len, boolean js_math, boolean js_imap, boolean js_packed, boolean js_hiero) { + if (stmt_insert == null) stmt_insert = Db_stmt_.new_insert_(provider, Tbl_name, Flds__all); + try { + stmt_insert.Clear() + .Val_int_(page_id).Val_int_(wtxt_len).Val_int_(row_orig_len).Val_int_(row_zip_len).Val_int_(body_len).Val_int_(display_ttl_len).Val_int_(content_sub_len).Val_int_(sidebar_div_len) + .Val_byte_by_bool_(js_math).Val_byte_by_bool_(js_imap).Val_byte_by_bool_(js_packed).Val_byte_by_bool_(js_hiero) + .Exec_insert(); + } + catch (Exception exc) {stmt_insert = null; throw Err_.err_(exc, "stmt failed");} // must reset stmt, else next call will fail + } + public void Rls_all() { + if (stmt_insert != null) {stmt_insert.Rls(); stmt_insert = null;} + provider = null; + } + public static final String Tbl_name = "hdump_stats" + , Fld_page_id = "page_id", Fld_wtxt_len = "wtxt_len", Fld_row_orig_len = "row_orig_len", Fld_row_zip_len = "row_zip_len" + , Fld_body_len = "body_len", Fld_display_ttl_len = "display_ttl_len", Fld_content_sub_len = "content_sub_len", Fld_sidebar_div_len = "sidebar_div_len" + , Fld_js_math = "js_math", Fld_js_imap = "js_imap", Fld_js_packed = "js_packed", Fld_js_hiero = "js_hiero" + ; + private static final String[] Flds__all = new String[] {Fld_page_id, Fld_wtxt_len, Fld_row_orig_len, Fld_row_zip_len, Fld_body_len, Fld_display_ttl_len, Fld_content_sub_len, Fld_sidebar_div_len, Fld_js_math, Fld_js_imap, Fld_js_packed, Fld_js_hiero}; + public static final String Tbl_sql = String_.Concat_lines_nl + ( "CREATE TABLE IF NOT EXISTS hdump_stats" + , "( page_id integer NOT NULL PRIMARY KEY" + , ", wtxt_len integer NOT NULL" + , ", row_orig_len integer NOT NULL" + , ", row_zip_len integer NOT NULL" + , ", body_len integer NOT NULL" + , ", display_ttl_len integer NOT NULL" + , ", content_sub_len integer NOT NULL" + , ", sidebar_div_len integer NOT NULL" + , ", js_math integer NOT NULL" + , ", js_imap integer NOT NULL" + , ", js_packed integer NOT NULL" + , ", js_hiero integer NOT NULL" + , ");" + ); +} diff --git a/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm.java b/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm.java new file mode 100644 index 000000000..d85148a46 --- /dev/null +++ b/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm.java @@ -0,0 +1,156 @@ +/* +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 . +*/ +package gplx.xowa.hdumps.srls; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; +import gplx.xowa.hdumps.core.*; +public interface Hpg_srl_itm { + byte Tid(); + int Load(Hdump_page hpg, byte[] bry, int bry_len, int itm_bgn, Int_obj_ref count_ref); + void Save(Hdump_page hpg, Bry_bfr bfr); +} +class Hpg_srl_itm_ { + public static final byte // SERIALIZED + Tid_body = 0 + , Tid_html_module = 1 + , Tid_display_ttl = 2 + , Tid_content_sub = 3 + , Tid_sidebar_div = 4 + ; + public static final Hpg_srl_itm[] Itms = new Hpg_srl_itm[] // NOTE: ary_idx must match tid above + { new Hpg_srl_itm__body() + , new Hpg_srl_itm__html_module() + , new Hpg_srl_itm__display_ttl() + , new Hpg_srl_itm__content_sub() + , new Hpg_srl_itm__sidebar_div() + }; + private static final int Base_255_int = 255; + private static final byte Base_255_byte = (byte)255; + public static void Save_bin_int_abrv(Bry_bfr bfr, int val_int) { // save int in binary little endian form; range from -2,080,766,977 to 2,147,483,648; 255^4 or 4,228,250,625 + if (val_int == 0) {bfr.Add_byte(Byte_ascii.Nil); return;} + long val = val_int; + if (val < 0) val = Int_.MaxValue + -val; + int count = 0; + while (val > 0) { + byte mod = (byte)(val % Base_255_int); + int adj = 0; + if (mod == 0) {mod = Base_255_byte; adj = 1;} // if 0, then set byte to 255; also set adj to 1 to properly decrement value + bfr.Add_byte(mod); + ++count; + val = (val - adj) / Base_255_int; + } + if (count < 4) bfr.Add_byte(Byte_ascii.Nil); + } + public static int Load_bin_int_abrv(byte[] bry, int bry_len, int bgn, Int_obj_ref count_ref) { + int end = bgn + 4; // read no more than 4 bytes + int count = 0; + long rv = 0; int mult = 1; + for (int i = bgn; i < end; ++i) { + if (i == bry_len) break; + else { + ++count; + int b = bry[i] & 0xFF; // PATCH.JAVA:need to convert to unsigned byte + if (b == 0) break; + rv += (b * mult); + mult *= Base_255_int; + } + } + if (rv > Int_.MaxValue) { + rv -= Int_.MaxValue; + rv *= -1; + } + count_ref.Val_(count); + return (int)rv; + } +} +abstract class Hpg_srl_itm__blob_base implements Hpg_srl_itm { + public abstract byte Tid(); + public void Save_tid_n_() {save_tid = false;} private boolean save_tid = true; + public void Save(Hdump_page hpg, Bry_bfr bfr) { + byte[] bry = Save_itm(hpg); if (bry == null) return; + int len = bry.length; if (len == 0) return; + if (save_tid) // body won't save tid + bfr.Add_byte(this.Tid()); + Hpg_srl_itm_.Save_bin_int_abrv(bfr, len); + bfr.Add(bry); + } + public int Load(Hdump_page hpg, byte[] bry, int bry_len, int itm_bgn, Int_obj_ref count_ref) { + int itm_len = Hpg_srl_itm_.Load_bin_int_abrv(bry, bry_len, itm_bgn, count_ref); if (itm_len == -1) throw Err_.new_("bry_itm has invalid len: page={0} tid={1}", hpg.Page_id(), this.Tid()); + int data_bgn = itm_bgn + count_ref.Val(); + if (itm_len == 0) return data_bgn; + int data_end = data_bgn + itm_len; + byte[] itm_data = Bry_.Mid(bry, data_bgn, data_end); + this.Load_itm(hpg, itm_data); + return data_end - itm_bgn; + } + public abstract void Load_itm(Hdump_page hpg, byte[] data); + public abstract byte[] Save_itm(Hdump_page hpg); +} +class Hpg_srl_itm__body extends Hpg_srl_itm__blob_base { + public Hpg_srl_itm__body() {this.Save_tid_n_();} + @Override public byte Tid() {return Hpg_srl_itm_.Tid_body;} + @Override public byte[] Save_itm(Hdump_page hpg) {return hpg.Page_body();} + @Override public void Load_itm(Hdump_page hpg, byte[] data) {hpg.Page_body_(data);} +} +class Hpg_srl_itm__display_ttl extends Hpg_srl_itm__blob_base { + @Override public byte Tid() {return Hpg_srl_itm_.Tid_display_ttl;} + @Override public byte[] Save_itm(Hdump_page hpg) {return hpg.Display_ttl();} + @Override public void Load_itm(Hdump_page hpg, byte[] data) {hpg.Display_ttl_(data);} +} +class Hpg_srl_itm__content_sub extends Hpg_srl_itm__blob_base { + @Override public byte Tid() {return Hpg_srl_itm_.Tid_content_sub;} + @Override public byte[] Save_itm(Hdump_page hpg) {return hpg.Content_sub();} + @Override public void Load_itm(Hdump_page hpg, byte[] data) {hpg.Content_sub_(data);} +} +class Hpg_srl_itm__sidebar_div extends Hpg_srl_itm__blob_base { + @Override public byte Tid() {return Hpg_srl_itm_.Tid_sidebar_div;} + @Override public byte[] Save_itm(Hdump_page hpg) {return hpg.Sidebar_div();} + @Override public void Load_itm(Hdump_page hpg, byte[] data) {hpg.Sidebar_div_(data);} +} +class Hpg_srl_itm__html_module implements Hpg_srl_itm { + public byte Tid() {return Hpg_srl_itm_.Tid_html_module;} + public int Load(Hdump_page hpg, byte[] bry, int bry_len, int itm_bgn, Int_obj_ref count_ref) { + itm_bgn += 2; // skip bin_int_abrv of [1, 0] + byte flag = bry[itm_bgn]; + hpg.Module_mgr().Init(Enm_.Has_byte(flag, Tid_math), Enm_.Has_byte(flag, Tid_imap), Enm_.Has_byte(flag, Tid_packed), Enm_.Has_byte(flag, Tid_hiero)); + return 3; + } + public void Save(Hdump_page hpg, Bry_bfr bfr) { + byte flag = Calc_flag(hpg); + if (flag == 0) return; + bfr.Add_byte(this.Tid()); + Hpg_srl_itm_.Save_bin_int_abrv(bfr, 1); + bfr.Add_byte(flag); + } + private static byte Calc_flag(Hdump_page hpg) { + Hdump_module_mgr module_mgr = hpg.Module_mgr(); + return Calc_flag(module_mgr.Math_exists(), module_mgr.Imap_exists(), module_mgr.Gallery_packed_exists(), module_mgr.Hiero_exists()); + } + public static byte Calc_flag(boolean math, boolean imap, boolean packed, boolean hiero) { + byte rv = 0; + if (math) rv = Enm_.Add_byte(rv, Tid_math); + if (imap) rv = Enm_.Add_byte(rv, Tid_imap); + if (packed) rv = Enm_.Add_byte(rv, Tid_packed); + if (hiero) rv = Enm_.Add_byte(rv, Tid_hiero); + return rv; + } + private static final byte // SERIALIZED; only supports 8 different types + Tid_math = 1 + , Tid_imap = 2 + , Tid_packed = 4 + , Tid_hiero = 8 + ; +} diff --git a/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm__tst.java b/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm__tst.java new file mode 100644 index 000000000..d362cddb1 --- /dev/null +++ b/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm__tst.java @@ -0,0 +1,52 @@ +/* +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 . +*/ +package gplx.xowa.hdumps.srls; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; +import org.junit.*; +public class Hpg_srl_itm__tst { + @Before public void init() {fxt.Clear();} private Hpg_srl_itm__fxt fxt = new Hpg_srl_itm__fxt(); + @Test public void Srl() { + fxt.Test_srl( 0, 0); + fxt.Test_srl( 1, 1, 0); + fxt.Test_srl( 255, 255, 0); + fxt.Test_srl( 256, 1, 1, 0); + fxt.Test_srl( 257, 2, 1, 0); + fxt.Test_srl( 510, 255, 1, 0); + fxt.Test_srl( 511, 1, 2, 0); + fxt.Test_srl( 512, 2, 2, 0); + fxt.Test_srl( 65280, 255, 255, 0); + fxt.Test_srl( 65281, 1, 1, 1, 0); + fxt.Test_srl( 16646655, 255, 255, 255, 0); + fxt.Test_srl( 16646656, 1, 1, 1, 1); + fxt.Test_srl( 16646657, 2, 1, 1, 1); + fxt.Test_srl(Int_.MaxValue, 127, 129, 130, 129); + fxt.Test_srl( -1, 128, 129, 130, 129); + fxt.Test_srl( -2, 129, 129, 130, 129); + } +} +class Hpg_srl_itm__fxt { + private Bry_bfr bfr = Bry_bfr.reset_(8); private Int_obj_ref read = Int_obj_ref.zero_(); + public void Clear() {bfr.Clear();} + public void Test_srl(int val, int... bytes) { + Hpg_srl_itm_.Save_bin_int_abrv(bfr, val); + byte[] save = bfr.Xto_bry_and_clear(); + Tfds.Eq_ary(Bry_.ints_(bytes), save, "save"); + int load = Hpg_srl_itm_.Load_bin_int_abrv(save, save.length, 0, read); + Tfds.Eq(val, load, "load"); + Tfds.Eq(bytes.length, read.Val(), "load_read"); + } +} diff --git a/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm_tst.java b/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm_tst.java new file mode 100644 index 000000000..90ac638dc --- /dev/null +++ b/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_itm_tst.java @@ -0,0 +1,99 @@ +/* +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 . +*/ +package gplx.xowa.hdumps.srls; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; +import org.junit.*; import gplx.xowa.hdumps.core.*; +public class Hpg_srl_itm_tst { + @Before public void init() {fxt.Clear();} private Hpg_srl_itm_fxt fxt = new Hpg_srl_itm_fxt(); + @Test public void Body() { + fxt.Test_page(fxt.Make_page().Body_("A"), fxt.Make_srl_body("A")); + } + @Test public void Html_modules() { + fxt.Test_page(fxt.Make_page().Body_("A").Html_modules_(Bool_.Y, Bool_.N, Bool_.Y, Bool_.N), fxt.Make_srl_body("A"), fxt.Make_srl_html_modules(Bool_.Y, Bool_.N, Bool_.Y, Bool_.N)); + } + @Test public void Body_all() { + fxt.Test_page(fxt.Make_page().Body_("A").Html_modules_(Bool_.Y, Bool_.N, Bool_.Y, Bool_.N).Display_ttl_("B").Content_sub_("C").Sidebar_div_("D") + , fxt.Make_srl_body("A") + , fxt.Make_srl_html_modules(Bool_.Y, Bool_.N, Bool_.Y, Bool_.N) + , fxt.Make_srl_display_ttl("B") + , fxt.Make_srl_content_sub("C") + , fxt.Make_srl_sidebar_div("D") + ); + } +} +class Hpg_srl_itm_fxt { + private Bry_bfr bfr = Bry_bfr.reset_(8); + public void Clear() {bfr.Clear();} + public Hdump_page_mok Make_page() {return new Hdump_page_mok();} + public Hpg_srl_itm_mok Make_srl_body(String s) {return Make_srl(Hpg_srl_itm_.Tid_body, s);} + public Hpg_srl_itm_mok Make_srl_display_ttl(String s) {return Make_srl(Hpg_srl_itm_.Tid_display_ttl, s);} + public Hpg_srl_itm_mok Make_srl_content_sub(String s) {return Make_srl(Hpg_srl_itm_.Tid_content_sub, s);} + public Hpg_srl_itm_mok Make_srl_sidebar_div(String s) {return Make_srl(Hpg_srl_itm_.Tid_sidebar_div, s);} + public Hpg_srl_itm_mok Make_srl(byte tid, String s) {return new Hpg_srl_itm_mok(tid, Bry_.new_utf8_(s));} + public Hpg_srl_itm_mok Make_srl_html_modules(boolean... v) { + return new Hpg_srl_itm_mok(Hpg_srl_itm_.Tid_html_module, new byte[] {Hpg_srl_itm__html_module.Calc_flag(v[0], v[1], v[2], v[3])}); + } + public void Test_page(Hdump_page_mok hpg_mok, Hpg_srl_itm_mok... expd_itms) { + Hdump_page hpg = hpg_mok.Xto_hdump_page(); + Hpg_srl_mgr._i_.Save(hpg, bfr); + byte[] actl = bfr.Xto_bry_and_clear(); + Tfds.Eq_ary(Hpg_srl_itm_mok.Xto_bry(bfr, expd_itms), actl); + Hdump_page actl_hpg = new Hdump_page(); + Hpg_srl_mgr._i_.Load(actl_hpg, actl); + Hpg_srl_mgr._i_.Save(hpg, bfr); + Tfds.Eq_ary(actl, bfr.Xto_bry_and_clear()); + } +} +class Hdump_page_mok { + public byte[] Body() {return body;} public Hdump_page_mok Body_(String v) {body = Bry_.new_utf8_(v); return this;} private byte[] body; + public boolean[] Html_modules() {return html_modules;} public Hdump_page_mok Html_modules_(boolean... v) {html_modules = v; return this;} private boolean[] html_modules; + public byte[] Display_ttl() {return display_ttl;} public Hdump_page_mok Display_ttl_(String v) {display_ttl = Bry_.new_utf8_(v); return this;} private byte[] display_ttl; + public byte[] Content_sub() {return content_sub;} public Hdump_page_mok Content_sub_(String v) {content_sub = Bry_.new_utf8_(v); return this;} private byte[] content_sub; + public byte[] Sidebar_div() {return sidebar_div;} public Hdump_page_mok Sidebar_div_(String v) {sidebar_div = Bry_.new_utf8_(v); return this;} private byte[] sidebar_div; + public Hdump_page Xto_hdump_page() { + Hdump_page rv = new Hdump_page(); + rv.Page_body_(body); + Hdump_module_mgr mod_mgr = rv.Module_mgr(); + if (html_modules != null) { + mod_mgr.Math_exists_(html_modules[0]); + mod_mgr.Imap_exists_(html_modules[1]); + mod_mgr.Gallery_packed_exists_(html_modules[2]); + mod_mgr.Hiero_exists_(html_modules[3]); + } + rv.Display_ttl_(display_ttl); + rv.Content_sub_(content_sub); + rv.Sidebar_div_(sidebar_div); + return rv; + } +} +class Hpg_srl_itm_mok { + public Hpg_srl_itm_mok(byte tid, byte[] data) {this.tid = tid; this.data = data;} + public byte Tid() {return tid;} private final byte tid; + public int Len() {return data.length;} + public byte[] Data() {return data;} private final byte[] data; + public static byte[] Xto_bry(Bry_bfr bfr, Hpg_srl_itm_mok[] ary) { + int len = ary.length; + for (int i = 0; i < len; ++i) { + Hpg_srl_itm_mok itm = ary[i]; + if (itm.Tid() != Hpg_srl_itm_.Tid_body) + bfr.Add_byte(itm.Tid()); + Hpg_srl_itm_.Save_bin_int_abrv(bfr, itm.Len()); + bfr.Add(itm.Data()); + } + return bfr.Xto_bry_and_clear(); + } +} diff --git a/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_mgr.java b/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_mgr.java new file mode 100644 index 000000000..e0d4c4967 --- /dev/null +++ b/400_xowa/src/gplx/xowa/hdumps/srls/Hpg_srl_mgr.java @@ -0,0 +1,40 @@ +/* +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 . +*/ +package gplx.xowa.hdumps.srls; import gplx.*; import gplx.xowa.*; import gplx.xowa.hdumps.*; +import gplx.xowa.hdumps.core.*; +public class Hpg_srl_mgr { + private Int_obj_ref count_ref = Int_obj_ref.zero_(); + public Hpg_srl_mgr(Hpg_srl_itm[] itm_ary) {this.itm_ary = itm_ary;} + public Hpg_srl_itm Itm_body() {return itm_body;} private final Hpg_srl_itm itm_body = new Hpg_srl_itm__body(); + public Hpg_srl_itm[] Itm_ary() {return itm_ary;} private final Hpg_srl_itm[] itm_ary; + public void Load(Hdump_page hpg, byte[] bry) { + if (bry == null) return; + int bry_len = bry.length; if (bry_len == 0) return; + int pos = itm_body.Load(hpg, bry, bry_len, 0, count_ref); // assume every page has a body; saves 1 byte by not specifying tid for body + while (pos < bry_len) { + byte itm_tid = bry[pos]; // itm_tid is always 1-byte + Hpg_srl_itm itm_parser = itm_ary[itm_tid]; // itm_tid always matches itm_ary's idx + pos += itm_parser.Load(hpg, bry, bry_len, pos + 1, count_ref) + 1; // +1 to skip tid + } + } + public void Save(Hdump_page hpg, Bry_bfr bfr) { + for (Hpg_srl_itm itm : itm_ary) + itm.Save(hpg, bfr); + } + public static final Hpg_srl_mgr _i_ = new Hpg_srl_mgr(Hpg_srl_itm_.Itms); +} diff --git a/400_xowa/src/gplx/xowa/html/Xoh_html_wtr.java b/400_xowa/src/gplx/xowa/html/Xoh_html_wtr.java index 2d226b2a5..4612ab193 100644 --- a/400_xowa/src/gplx/xowa/html/Xoh_html_wtr.java +++ b/400_xowa/src/gplx/xowa/html/Xoh_html_wtr.java @@ -42,7 +42,7 @@ public class Xoh_html_wtr { public void Write_all(Bry_bfr bfr, Xop_ctx ctx, Xoh_wtr_ctx hctx, byte[] src, Xop_root_tkn root) { try { indent_level = 0; this.page = ctx.Cur_page(); - page.Xwiki_langs().Clear(); // HACK: always clear langs; necessary for reload + page.Slink_list().Clear(); // HACK: always clear langs; necessary for reload lnki_wtr.Init_by_page(ctx, hctx, src, ctx.Cur_page()); Write_tkn(bfr, ctx, hctx, src, null, -1, root); } @@ -106,7 +106,7 @@ public class Xoh_html_wtr { @gplx.Virtual public void Hdr(Xop_ctx ctx, Xoh_wtr_ctx hctx, Bry_bfr bfr, byte[] src, Xop_hdr_tkn hdr) { // page.Hdrs_id_bld(hdr, src); if (hdr.Hdr_html_first() && cfg.Toc_show() && !page.Hdr_mgr().Toc_manual()) { // __TOC__ not specified; place at top; NOTE: if __TOC__ was specified, then it would be placed wherever __TOC__ appears - wiki.Html_mgr().Toc_mgr().Html(ctx.Cur_page(), src, bfr); + wiki.Html_mgr().Toc_mgr().Html(ctx.Cur_page(), hctx, src, bfr); } int hdr_len = hdr.Hdr_len(); if (hdr_len > 0) { // NOTE: need to check hdr_len b/c it could be dangling @@ -289,7 +289,7 @@ public class Xoh_html_wtr { if (hctx.Mode_is_alt()) return; switch (under.Under_tid()) { case Xol_kwd_grp_.Id_toc: - wiki.Html_mgr().Toc_mgr().Html(page, src, bfr); + wiki.Html_mgr().Toc_mgr().Html(page, hctx, src, bfr); break; case Xol_kwd_grp_.Id_notoc: case Xol_kwd_grp_.Id_forcetoc: // NOTE: skip output; changes flag on page only break; diff --git a/400_xowa/src/gplx/xowa/html/Xoh_page_wtr_wkr.java b/400_xowa/src/gplx/xowa/html/Xoh_page_wtr_wkr.java index 7a9102377..d0c620f0d 100644 --- a/400_xowa/src/gplx/xowa/html/Xoh_page_wtr_wkr.java +++ b/400_xowa/src/gplx/xowa/html/Xoh_page_wtr_wkr.java @@ -37,7 +37,7 @@ public class Xoh_page_wtr_wkr implements Bry_fmtr_arg { case Xopg_view_mode.Tid_edit: fmtr = mgr.Page_edit_fmtr(); break; case Xopg_view_mode.Tid_html: fmtr = mgr.Page_read_fmtr(); view_mode = Xopg_view_mode.Tid_read; break; // set view_mode to read, so that "read" is highlighted in HTML case Xopg_view_mode.Tid_read: fmtr = mgr.Page_read_fmtr(); - ctx.Cur_page().Lnki_redlinks_mgr().Page_bgn(); // not sure if this is the best place to put it, but redlinks (a) must only fire once; (b) must fire before html generation; (c) cannot fire during edit (preview will handle separately) + ctx.Cur_page().Lnki_redlinks_mgr().Clear(); // not sure if this is the best place to put it, but redlinks (a) must only fire once; (b) must fire before html generation; (c) cannot fire during edit (preview will handle separately) break; } Write_page(html_bfr, app, wiki, mgr, page, view_mode, fmtr, this); diff --git a/400_xowa/src/gplx/xowa/html/lnkis/Xoh_lnki_wtr.java b/400_xowa/src/gplx/xowa/html/lnkis/Xoh_lnki_wtr.java index 6216a90f8..d35ca9107 100644 --- a/400_xowa/src/gplx/xowa/html/lnkis/Xoh_lnki_wtr.java +++ b/400_xowa/src/gplx/xowa/html/lnkis/Xoh_lnki_wtr.java @@ -17,14 +17,15 @@ along with this program. If not, see . */ package gplx.xowa.html.lnkis; import gplx.*; import gplx.xowa.*; import gplx.xowa.html.*; import gplx.html.*; import gplx.xowa.files.*; import gplx.xowa.parsers.lnkis.redlinks.*; import gplx.xowa.users.history.*; import gplx.xowa.xtns.pfuncs.ttls.*; import gplx.xowa.xtns.relatedSites.*; -import gplx.xowa.wikis.xwikis.*; +import gplx.xowa.wikis.xwikis.*; import gplx.xowa.xtns.wdatas.core.*; import gplx.xowa.hdumps.hzips.*; public class Xoh_lnki_wtr { private Xoa_app app; private Xow_wiki wiki; private Xoa_page page; private Xop_ctx ctx; private Xoh_html_wtr_cfg cfg; - private Xou_history_mgr history_mgr; + private Xou_history_mgr history_mgr; private Xop_lnki_caption_wtr_tkn caption_tkn_wtr; private Xop_lnki_caption_wtr_bry caption_bry_wtr; private Xop_lnki_logger_redlinks_mgr redlinks_mgr; + private Xoa_hzip_mgr hzip_mgr; public Xoh_lnki_wtr(Xoh_html_wtr html_wtr, Xow_wiki wiki, Xow_html_mgr html_mgr, Xoh_html_wtr_cfg cfg) { caption_tkn_wtr = new Xop_lnki_caption_wtr_tkn(html_wtr); caption_bry_wtr = new Xop_lnki_caption_wtr_bry(); @@ -52,7 +53,8 @@ public class Xoh_lnki_wtr { && xwiki_lang.Type_is_xwiki_lang(wiki.Domain_itm().Lang_orig_uid())// NOTE: use Lang_orig_id to handle xwikis between s.w and en.w; PAGE:s.q:Anonymous DATE:2014-09-10 && !lnki_ttl.ForceLiteralLink() // not literal; [[:en:A]] ) { - page.Xwiki_langs().Add(lnki_ttl); + Wdata_sitelink_itm slink = new Wdata_sitelink_itm(null, null, null).Page_ttl_(lnki_ttl); + page.Slink_list().Add(slink); return; } boolean literal_link = lnki_ttl.ForceLiteralLink(); // NOTE: if literal link, then override ns behavior; for File, do not show image; for Ctg, do not display at bottom of page @@ -91,11 +93,16 @@ public class Xoh_lnki_wtr { return; } } - if (lnki.Xtn_sites_link()) return; // lnki marked for relatedSites; don't write to page + if (lnki.Xtn_sites_link()) return; // lnki marked for relatedSites; don't write to page if (hctx.Mode_is_alt()) Write_caption(bfr, ctx, hctx, src, lnki, ttl_bry, true, caption_wkr); else { - bfr.Add(Xoh_consts.A_bgn); // '. +*/ +package gplx.xowa.pages; import gplx.*; import gplx.xowa.*; +public class Xopg_revision_data { + public int Id() {return id;} public Xopg_revision_data Id_(int v) {id = v; return this;} private int id; + public DateAdp Modified_on() {return modified_on;} public Xopg_revision_data Modified_on_(DateAdp v) {modified_on = v; return this;} private DateAdp modified_on = DateAdp_.MinValue; + public byte[] User() {return user;} public Xopg_revision_data User_(byte[] v) {user = v; return this;} private byte[] user = Bry_.Empty; + public byte[] Protection_level() {return protection_level;} public Xopg_revision_data Protection_level_(byte[] v) {protection_level = v; return this;} private byte[] protection_level = Bry_.Empty; + public int Html_db_id() {return html_db_id;} public void Html_db_id_(int v) {html_db_id = v;} private int html_db_id = -1; + public void Clear() {}// NOTE: do not clear data b/c saving in Edit will call clear and id will be reset to 0 +} diff --git a/400_xowa/src/gplx/xowa/parsers/lnkis/redlinks/Xop_lnki_logger_redlinks_mgr.java b/400_xowa/src/gplx/xowa/parsers/lnkis/redlinks/Xop_lnki_logger_redlinks_mgr.java index a97674a5b..5c24bab74 100644 --- a/400_xowa/src/gplx/xowa/parsers/lnkis/redlinks/Xop_lnki_logger_redlinks_mgr.java +++ b/400_xowa/src/gplx/xowa/parsers/lnkis/redlinks/Xop_lnki_logger_redlinks_mgr.java @@ -26,7 +26,7 @@ public class Xop_lnki_logger_redlinks_mgr { public ListAdp Lnki_list() {return lnki_list;} private ListAdp lnki_list = ListAdp_.new_(); public boolean Log_enabled() {return log_enabled;} private boolean log_enabled = false; public Gfo_usr_dlg Usr_dlg() {return usr_dlg;} private Gfo_usr_dlg usr_dlg = null; - public void Page_bgn() { + public void Clear() { request_idx++; Xoa_app app = page.App(); log_enabled = app.User().Cfg_mgr().Log_mgr().Log_redlinks(); diff --git a/400_xowa/src/gplx/xowa/xtns/imaps/Imap_parser.java b/400_xowa/src/gplx/xowa/xtns/imaps/Imap_parser.java index 97fd3b294..492f59063 100644 --- a/400_xowa/src/gplx/xowa/xtns/imaps/Imap_parser.java +++ b/400_xowa/src/gplx/xowa/xtns/imaps/Imap_parser.java @@ -104,40 +104,35 @@ class Imap_parser { imap_dflt = new Imap_itm_dflt(); Init_link_owner(imap_dflt, src, itm_bgn, itm_end); } - private boolean Parse_shape(byte shape_tid, int tid_end_pos, int itm_bgn, int itm_end, int reqd_pts) { - int num_bgn = -1; // differs from MW parser which looks for link via regx, and then chops off rest; regx is difficult due to lnke; doing opposite approach which is eat numbers until something else - int pos = Bry_finder.Trim_fwd_space_tab(src, tid_end_pos, itm_end); - boolean reading_numbers = true; - int comma_pos_0 = -1; - while (reading_numbers) { - boolean last = pos == itm_end; + private boolean Parse_shape(byte shape_tid, int tid_end_pos, int itm_bgn, int itm_end, int reqd_pts) { + boolean shape_is_poly = shape_tid == Imap_itm_.Tid_shape_poly; + int pos = Bry_finder.Trim_fwd_space_tab(src, tid_end_pos, itm_end); // gobble any leading spaces + int grp_end = Bry_finder.Find_fwd(src, Byte_ascii.Brack_bgn, pos, itm_end); // find first "["; note that this is a lazy way of detecting start of lnki / lnke; MW has complicated regex, but hopefully this will be enough; DATE:2014-10-22 + if (grp_end == -1) {return Add_err(Bool_.Y, itm_bgn, itm_end, "No valid link was found");} + int num_bgn = -1, comma_pos = -1; + while (true) { + boolean last = pos == grp_end; byte b = last ? Byte_ascii.Space : src[pos]; switch (b) { - case Byte_ascii.Num_0: case Byte_ascii.Num_1: case Byte_ascii.Num_2: case Byte_ascii.Num_3: case Byte_ascii.Num_4: - case Byte_ascii.Num_5: case Byte_ascii.Num_6: case Byte_ascii.Num_7: case Byte_ascii.Num_8: case Byte_ascii.Num_9: - case Byte_ascii.Dash: case Byte_ascii.Dot: - if (num_bgn == -1) - num_bgn = pos; - ++pos; - break; - case Byte_ascii.Comma: - if (comma_pos_0 == -1) comma_pos_0 = pos; - if (num_bgn == -1) - num_bgn = pos; - ++pos; - break; - default: - int new_pos = Parse_shape_num(shape_tid, b, pos, num_bgn, pos, itm_end, comma_pos_0); - if (new_pos == -1) return Add_err(Bool_.Y, itm_bgn, itm_end, "imagemap_invalid_coord"); - if (new_pos == pos) // occurs when char is text - reading_numbers = false; - else - pos = Bry_finder.Trim_fwd_space_tab(src, new_pos, itm_end); - num_bgn = -1; - comma_pos_0 = -1; + case Byte_ascii.Comma: if (comma_pos == -1) comma_pos = pos; break; + default: if (num_bgn == -1) num_bgn = pos; break; + case Byte_ascii.Space: case Byte_ascii.Tab: + if (num_bgn != -1) { + byte[] num_bry = comma_pos == -1 ? Bry_.Mid(src, num_bgn, pos) : Bry_.Mid(src, num_bgn, comma_pos); // if commas exist, treat first as decimal; echo(intval(round('1,2,3,4' * 1))) -> 1; PAGE:fr.w:Gouesnou; DATE:2014-08-12 + double num = Bry_.Xto_double_or(num_bry, Double_.NaN); + if (Double_.IsNaN(num)) { + if (shape_is_poly) // poly code in ImageMap_body.php accepts invalid words and converts to 0; EX:"word1"; PAGE:uk.w:Стратосфера; DATE:2014-07-26 + num = 0; + else + return Add_err(Bool_.Y, itm_bgn, itm_end, "imagemap_invalid_coord"); + } + num_bgn = -1; comma_pos = -1; + pts.Add(Double_obj_val.new_(num)); + } break; } - if (last) reading_numbers = false; + if (last) break; + ++pos; } int pts_len = pts.Count(); if (reqd_pts == Reqd_poly) { @@ -181,33 +176,6 @@ class Imap_parser { } return null; } - private int Parse_shape_num(byte shape_tid, byte b, int pos, int num_bgn, int num_end, int itm_end, int comma_pos_0) { - double num = 0; - boolean shape_is_poly = shape_tid == Imap_itm_.Tid_shape_poly; - if (num_bgn == -1) { // 1st char is non-numeric; EX: "poly a" - if ( shape_is_poly // poly code in ImageMap_body.php accepts invalid words and converts to 0; EX:"poly1"; PAGE:uk.w:Стратосфера; DATE:2014-07-26 - && b != Byte_ascii.Brack_bgn // skip logic if "[" which may be beginning of lnki / lnke - ) { - num_end = Bry_finder.Find_fwd_until_space_or_tab(src, pos, itm_end); // gobble up rest of word and search forward for space / tab to - if (num_end == Bry_finder.Not_found) return -1; // space / tab not found; return -1 (fail) - num = 0; - } - else - return num_end; - } - else { - int parse_end = comma_pos_0 == -1 ? num_end : comma_pos_0; // if commas exist, treat first as decimal; echo(intval(round('1,2,3,4' * 1))) -> 1; PAGE:fr.w:Gouesnou; DATE:2014-08-12 - num = Bry_.XtoDoubleByPosOr(src, num_bgn, parse_end, Double_.NaN); - } - if (Double_.IsNaN(num)) { - if (shape_is_poly) // poly code in ImageMap_body.php accepts invalid words and converts to 0; EX:"poly 1a" - num = 0; - else - return -1; // invalid number; EX: "1.2.3" - } - pts.Add(Double_obj_val.new_(num)); - return Bry_finder.Trim_fwd_space_tab(src, num_end, itm_end); - } private int Parse_img(Imap_map imap, int itm_bgn, int itm_end, int src_end) { int img_bgn = Bry_finder.Trim_fwd_space_tab(src, itm_bgn, itm_end); // trim ws int img_end = Parse_img__get_img_end(itm_end, src_end); diff --git a/400_xowa/src/gplx/xowa/xtns/imaps/Imap_parser_tst.java b/400_xowa/src/gplx/xowa/xtns/imaps/Imap_parser_tst.java index 714a9e7fc..c64eb0740 100644 --- a/400_xowa/src/gplx/xowa/xtns/imaps/Imap_parser_tst.java +++ b/400_xowa/src/gplx/xowa/xtns/imaps/Imap_parser_tst.java @@ -24,6 +24,7 @@ public class Imap_parser_tst { @Test public void Circle_pass() {fxt.Test_shape("circle 1 2 3 [[A]]" , fxt.itm_circle_("[[A]]", 1, 2, 3));} @Test public void Poly_pass() {fxt.Test_shape("poly 1 2 3 4 5 6 [[A]]" , fxt.itm_poly_("[[A]]", 1, 2, 3, 4, 5, 6));} @Test public void Poly_pass_chars() {fxt.Test_shape("poly a b [[A]]" , fxt.itm_poly_("[[A]]", 0, 0));} // PURPOSE: non-numeric should be converted to 0; PAGE:uk.w:Стратосфера; DATE:2014-07-26 + @Test public void Poly_pass_chars_2() {fxt.Test_shape("poly 1a 2a [[A]]" , fxt.itm_poly_("[[A]]", 0, 0));} // PURPOSE: non-numeric should be converted to 0; PAGE:ru.w:Системный_блок; DATE:2014-10-22 @Test public void Poly_pass_dots() {fxt.Test_shape("poly 1.2 3.4 [[A]]" , fxt.itm_poly_("[[A]]", 1.2d, 3.4d));} // PURPOSE: make sure decimals are handled correctly @Test public void Poly_pass_commas() {fxt.Test_shape("poly 1, 2, 3, 4 [[A]]" , fxt.itm_poly_("[[A]]", 1, 2, 3, 4));} // PURPOSE: commas should be ignored; PAGE:de.w:Kaimnitz; DATE:2014-08-05 @Test public void Poly_pass_commas_2() {fxt.Test_shape("poly 1,2 3,4 [[A]]" , fxt.itm_poly_("[[A]]", 1, 3));} // PURPOSE: commas should be ignored for purpose of parse; PAGE:fr.w:Gouesnou; DATE:2014-08-12 diff --git a/400_xowa/src/gplx/xowa/xtns/pfuncs/pages/Pfunc_rev_props.java b/400_xowa/src/gplx/xowa/xtns/pfuncs/pages/Pfunc_rev_props.java index 882f3cffb..57147a12c 100644 --- a/400_xowa/src/gplx/xowa/xtns/pfuncs/pages/Pfunc_rev_props.java +++ b/400_xowa/src/gplx/xowa/xtns/pfuncs/pages/Pfunc_rev_props.java @@ -16,14 +16,15 @@ You should have received a copy of the GNU Affero General Public License along with this program. If not, see . */ package gplx.xowa.xtns.pfuncs.pages; import gplx.*; import gplx.xowa.*; import gplx.xowa.xtns.*; import gplx.xowa.xtns.pfuncs.*; +import gplx.xowa.pages.*; public class Pfunc_rev_props extends Pf_func_base { @Override public void Func_evaluate(Xop_ctx ctx, byte[] src, Xot_invk caller, Xot_invk self, Bry_bfr bfr) { byte[] argx = Eval_argx(ctx, src, caller, self); - Xoa_revision_data revision_data = ctx.Cur_page().Revision_data(); + Xopg_revision_data rev_data = ctx.Cur_page().Revision_data(); switch (id) { case Xol_kwd_grp_.Id_page_id: - case Xol_kwd_grp_.Id_rev_id: bfr.Add_int_variable(ctx.Cur_page().Revision_data().Id()); break; // NOTE: making rev_id and page_id interchangeable; XOWA does not store rev_id - case Xol_kwd_grp_.Id_rev_user: bfr.Add(revision_data.User()); break; + case Xol_kwd_grp_.Id_rev_id: bfr.Add_int_variable(ctx.Cur_page().Revision_data().Id()); break; // NOTE: making rev_id and page_id interchangeable; XOWA does not store rev_id + case Xol_kwd_grp_.Id_rev_user: bfr.Add(rev_data.User()); break; case Xol_kwd_grp_.Id_rev_pagesize: if (argx.length > 0) { Xoa_ttl argx_ttl = Xoa_ttl.parse_(ctx.Wiki(), argx); @@ -39,7 +40,7 @@ public class Pfunc_rev_props extends Pf_func_base { } bfr.Add_byte(Byte_ascii.Num_0); break; - case Xol_kwd_grp_.Id_rev_protectionlevel: bfr.Add(revision_data.Protection_level()); break; + case Xol_kwd_grp_.Id_rev_protectionlevel: bfr.Add(rev_data.Protection_level()); break; default: throw Err_.unhandled(id); } } diff --git a/400_xowa/src/gplx/xowa/xtns/pfuncs/pages/Pfunc_rev_props_tst.java b/400_xowa/src/gplx/xowa/xtns/pfuncs/pages/Pfunc_rev_props_tst.java index d90556855..0a399a39e 100644 --- a/400_xowa/src/gplx/xowa/xtns/pfuncs/pages/Pfunc_rev_props_tst.java +++ b/400_xowa/src/gplx/xowa/xtns/pfuncs/pages/Pfunc_rev_props_tst.java @@ -21,8 +21,8 @@ public class Pfunc_rev_props_tst { private Xop_fxt fxt = new Xop_fxt(); @Before public void setup() {fxt.Reset(); fxt.Page().Revision_data().User_(Bry_.new_ascii_("user")).Protection_level_(Bry_.new_ascii_("normal"));} @After public void teardown() {} - @Test public void RevisionID() {fxt.Page().Revision_data().Id_(1); fxt.Test_parse_tmpl_str_test("{{REVISIONID}}" , "{{test}}", "1");} - @Test public void PageID() {fxt.Page().Revision_data().Id_(1); fxt.Test_parse_tmpl_str_test("{{PAGEID}}" , "{{test}}", "1");} + @Test public void RevisionID() {fxt.Page().Revision_data().Id_(1); fxt.Test_parse_tmpl_str_test("{{REVISIONID}}" , "{{test}}", "1");} + @Test public void PageID() {fxt.Page().Revision_data().Id_(1); fxt.Test_parse_tmpl_str_test("{{PAGEID}}" , "{{test}}", "1");} @Test public void RevisionUser() {fxt.Test_parse_tmpl_str_test("{{REVISIONUSER}}" , "{{test}}", "user");} @Test public void PageSize() {fxt.Test_parse_tmpl_str_test("{{PAGESIZE:Test page}}" , "{{test}}", "0");} @Test public void ProtectionLevel() {fxt.Test_parse_tmpl_str_test("{{PROTECTIONLEVEL}}" , "{{test}}", "normal");} diff --git a/400_xowa/src/gplx/xowa/xtns/poems/Poem_nde.java b/400_xowa/src/gplx/xowa/xtns/poems/Poem_nde.java index 691c5c06b..ed7d5a11f 100644 --- a/400_xowa/src/gplx/xowa/xtns/poems/Poem_nde.java +++ b/400_xowa/src/gplx/xowa/xtns/poems/Poem_nde.java @@ -43,10 +43,10 @@ public class Poem_nde implements Xox_xnde { boolean indent_enabled = false; if (line_is_1st) line_is_1st = false; else { - if (Bry_.Match(src, line_bgn, line_bgn + Comment_marker.length, Comment_marker)) + if (Bry_.Match(src, line_bgn, line_bgn + Xowa_br_mark.length, Xowa_br_mark)) // "
\n" already inserted by XOWA; do not insert again; DATE:2014-10-20 bfr.Add_byte_nl(); else - bfr.Add(Html_tag_.Br_inl).Add_byte_nl().Add(Comment_marker); // add "
\n" unless 1st line; EX: "\n\s" should not add leading "
\n" + bfr.Add(Html_tag_.Br_inl).Add_byte_nl().Add(Xowa_br_mark); // add "
\n" unless 1st line; EX: "\n\s" should not add leading "
\n" } switch (src[line_bgn]) { case Byte_ascii.Space: // "\n\s" -> "\n " @@ -78,6 +78,6 @@ public class Poem_nde implements Xox_xnde { , Div_poem_end = Bry_.new_ascii_("\n

\n") , Indent_bgn = Bry_.new_ascii_("\n") - , Comment_marker = Bry_.new_ascii_("") + , Xowa_br_mark = Bry_.new_ascii_("") ; } diff --git a/400_xowa/src/gplx/xowa/xtns/poems/Poem_nde_tst.java b/400_xowa/src/gplx/xowa/xtns/poems/Poem_nde_tst.java index 6f16f829a..e67ddc387 100644 --- a/400_xowa/src/gplx/xowa/xtns/poems/Poem_nde_tst.java +++ b/400_xowa/src/gplx/xowa/xtns/poems/Poem_nde_tst.java @@ -260,7 +260,7 @@ public class Poem_nde_tst { , "b
" , "
" , "

" - , "c
" // NOTE: 1
not 2 + , "c
" // NOTE: "
" not "

" , "d
" , " " , "

" diff --git a/400_xowa/src/gplx/xowa/xtns/scribunto/Scrib_core.java b/400_xowa/src/gplx/xowa/xtns/scribunto/Scrib_core.java index 0dd285de1..d3fc8c1b4 100644 --- a/400_xowa/src/gplx/xowa/xtns/scribunto/Scrib_core.java +++ b/400_xowa/src/gplx/xowa/xtns/scribunto/Scrib_core.java @@ -208,7 +208,8 @@ public class Scrib_core { || core_invalidate_when_page_changes // core marked invalidated b/c of error in {{#invoke}} but won't be regen'd until page changes; invalidate now; PAGE:th.d:all; DATE:2014-10-03 ) { core_invalidate_when_page_changes = false; - if (Bry_.Eq(page.Wiki().Domain_bry(), core.Cur_wiki())) // current page is in same wiki as last page + if ( core != null // null check + && Bry_.Eq(page.Wiki().Domain_bry(), core.Cur_wiki())) // current page is in same wiki as last page core.When_page_changed(page); else // current page is in different wiki Core_invalidate(); // invalidate scrib engine; note that lua will cache chunks by Module name and two modules in two different wikis can have the same name, but different data: EX:Module:Citation/CS1/Configuration and enwiki / zhwiki; DATE:2014-03-21 diff --git a/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl.java b/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl.java index bfabc4b70..c19cae250 100644 --- a/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl.java +++ b/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl.java @@ -97,20 +97,20 @@ class Scrib_lib_wikibase_srl { KeyVal[] rv = new KeyVal[len]; for (int i = 0; i < len; i++) { Wdata_claim_itm_core itm = grp.Get_at(i); - rv[i] = KeyVal_.int_(i + base_adj, Srl_claims_prop_itm(pid, itm)); // NOTE: must be super 0 or super 1; DATE:2014-05-09 + rv[i] = KeyVal_.int_(i + base_adj, Srl_claims_prop_itm(pid, itm, base_adj)); // NOTE: must be super 0 or super 1; DATE:2014-05-09 } return rv; } - private static KeyVal[] Srl_claims_prop_itm(String pid, Wdata_claim_itm_core itm) { + private static KeyVal[] Srl_claims_prop_itm(String pid, Wdata_claim_itm_core itm, int base_adj) { ListAdp list = ListAdp_.new_(); - list.Add(KeyVal_.new_("id", String_.new_utf8_(itm.Wguid()))); + list.Add(KeyVal_.new_("id", pid)); list.Add(KeyVal_.new_("mainsnak", Srl_claims_prop_itm_core(pid, itm))); list.Add(KeyVal_.new_(Wdata_dict_claim_v1.Str_rank, Wdata_dict_rank.Xto_str(itm.Rank_tid()))); list.Add(KeyVal_.new_("type", itm.Prop_type())); - Srl_root(list, Wdata_dict_claim.Str_qualifiers, Srl_qualifiers(itm.Qualifiers())); + Srl_root(list, Wdata_dict_claim.Str_qualifiers, Srl_qualifiers(itm.Qualifiers(), base_adj)); return (KeyVal[])list.Xto_ary_and_clear(KeyVal.class); } - private static KeyVal[] Srl_qualifiers(Wdata_claim_grp_list list) { + private static KeyVal[] Srl_qualifiers(Wdata_claim_grp_list list, int base_adj) { if (list == null) return null; int list_len = list.Len(); if (list_len == 0) return KeyVal_.Ary_empty; ListAdp rv = ListAdp_.new_(); @@ -122,7 +122,7 @@ class Scrib_lib_wikibase_srl { String itm_pid = grp.Id_str(); for (int j = 0; j < grp_len; ++j) { Wdata_claim_itm_core itm = grp.Get_at(j); - pid_list.Add(KeyVal_.int_(j + ListAdp_.Base1, Srl_claims_prop_itm_core(itm_pid, itm))); + pid_list.Add(KeyVal_.int_(j + base_adj, Srl_claims_prop_itm_core(itm_pid, itm))); // NOTE: was originally "+ 1"; changed to base_adj; PAGE:ru.w:Tor ru.w:Кактусовые DATE:2014-10-25 } rv.Add(KeyVal_.new_(itm_pid, (KeyVal[])pid_list.Xto_ary_and_clear(KeyVal.class))); } @@ -147,5 +147,5 @@ class Scrib_lib_wikibase_srl { } } public static final String Key_type = "type", Key_value = "value"; - private static final KeyVal[] DataValue_nil = new KeyVal[] {KeyVal_.new_(Key_type, ""), KeyVal_.new_(Key_value, "")}; // NOTE: must return ""; null fails; EX:w:Joseph-Fran�ois_Malgaigne; DATE:2014-04-07 + private static final KeyVal[] DataValue_nil = new KeyVal[] {KeyVal_.new_(Key_type, ""), KeyVal_.new_(Key_value, "")}; // NOTE: must return ""; null fails; EX:w:Joseph-François_Malgaigne; DATE:2014-04-07 } diff --git a/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl_tst.java b/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl_tst.java index a2bfb4d62..970040a88 100644 --- a/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl_tst.java +++ b/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl_tst.java @@ -125,7 +125,7 @@ public class Scrib_lib_wikibase_srl_tst { ( "claims:" , " P2:" , " 1:" - , " id:null" + , " id:'P2'" , " mainsnak:" , " datavalue:" , " type:'string'" @@ -143,7 +143,7 @@ public class Scrib_lib_wikibase_srl_tst { ( "claims:" , " P2:" , " 1:" - , " id:null" + , " id:'P2'" , " mainsnak:" , " datavalue:" , " type:''" @@ -161,7 +161,7 @@ public class Scrib_lib_wikibase_srl_tst { ( "claims:" , " P2:" , " 1:" - , " id:null" + , " id:'P2'" , " mainsnak:" , " datavalue:" , " type:'wikibase-entityid'" @@ -181,7 +181,7 @@ public class Scrib_lib_wikibase_srl_tst { , "claims:" , " P2:" , " 0:" - , " id:null" + , " id:'P2'" , " mainsnak:" , " datavalue:" , " type:'wikibase-entityid'" @@ -194,7 +194,7 @@ public class Scrib_lib_wikibase_srl_tst { , " type:'statement'" , " p2:" , " 0:" - , " id:null" + , " id:'P2'" , " mainsnak:" , " datavalue:" , " type:'wikibase-entityid'" @@ -214,7 +214,7 @@ public class Scrib_lib_wikibase_srl_tst { ( "claims:" , " P2:" , " 1:" - , " id:null" + , " id:'P2'" , " mainsnak:" , " datavalue:" , " type:'time'" @@ -238,7 +238,7 @@ public class Scrib_lib_wikibase_srl_tst { ( "claims:" , " P2:" , " 1:" - , " id:null" + , " id:'P2'" , " mainsnak:" , " datavalue:" , " type:'globecoordinate'" @@ -261,7 +261,7 @@ public class Scrib_lib_wikibase_srl_tst { ( "claims:" , " P2:" , " 1:" - , " id:null" + , " id:'P2'" , " mainsnak:" , " datavalue:" , " type:'quantity'" @@ -277,6 +277,26 @@ public class Scrib_lib_wikibase_srl_tst { , "" ); } + @Test public void Claims_monolingualtext() {// PURPOSE.fix: type was mistakenly "language" instead of "monolingualtext" DATE:2014-10-21 + fxt.Init_prop(fxt.Wdata_fxt().Make_claim_monolingual(2, "en", "en_text")); + fxt.Test + ( "claims:" + , " P2:" + , " 1:" + , " id:'P2'" + , " mainsnak:" + , " datavalue:" + , " type:'monolingualtext'" + , " value:" + , " text:'en_text'" + , " language:'en'" + , " property:'P2'" + , " snaktype:'value'" + , " rank:'normal'" + , " type:'statement'" + , "" + ); + } @Test public void Qualifiers() { Wdata_wiki_mgr_fxt wdata_fxt = fxt.Wdata_fxt(); fxt.Init_prop(wdata_fxt.Make_claim_str(2, "Earth").Qualifiers_(wdata_fxt.Make_qualifiers(wdata_fxt.Make_qualifiers_grp(3, wdata_fxt.Make_claim_time(3, "2001-02-03 04:05:06"))))); @@ -284,7 +304,7 @@ public class Scrib_lib_wikibase_srl_tst { ( "claims:" , " P2:" , " 1:" - , " id:null" + , " id:'P2'" , " mainsnak:" , " datavalue:" , " type:'string'" diff --git a/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl_visitor.java b/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl_visitor.java index 379facd7e..2ad702db9 100644 --- a/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl_visitor.java +++ b/400_xowa/src/gplx/xowa/xtns/scribunto/lib/Scrib_lib_wikibase_srl_visitor.java @@ -38,7 +38,7 @@ class Scrib_lib_wikibase_srl_visitor implements Wdata_claim_visitor { } public void Visit_monolingualtext(Wdata_claim_itm_monolingualtext itm) { rv = new KeyVal[2]; - rv[0] = KeyVal_.new_(Scrib_lib_wikibase_srl.Key_type, Wdata_dict_value_monolingualtext.Str_language); + rv[0] = KeyVal_.new_(Scrib_lib_wikibase_srl.Key_type, Wdata_dict_val_tid.Str_monolingualtext); rv[1] = KeyVal_.new_(Scrib_lib_wikibase_srl.Key_value, Monolingualtext_value(itm)); } private static KeyVal[] Monolingualtext_value(Wdata_claim_itm_monolingualtext itm) { diff --git a/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_wiki_mgr_fxt.java b/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_wiki_mgr_fxt.java index f07f1e627..9f1e61c28 100644 --- a/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_wiki_mgr_fxt.java +++ b/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_wiki_mgr_fxt.java @@ -165,8 +165,8 @@ public class Wdata_wiki_mgr_fxt { int len = list.Count(); String[] rv = new String[len]; for (int i = 0; i < len; i++) { - Xoa_ttl itm = (Xoa_ttl)list.FetchAt(i); - rv[i] = String_.new_ascii_(itm.Page_db()); + Wdata_sitelink_itm itm = (Wdata_sitelink_itm)list.FetchAt(i); + rv[i] = String_.new_ascii_(itm.Page_ttl().Page_db()); } tmp_langs.Clear(); return rv; diff --git a/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_xwiki_link_wtr.java b/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_xwiki_link_wtr.java index fcb681ce5..dc8bc547a 100644 --- a/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_xwiki_link_wtr.java +++ b/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_xwiki_link_wtr.java @@ -20,13 +20,13 @@ import gplx.json.*; import gplx.xowa.wikis.*; import gplx.xowa.wikis.xwikis.*; i public class Wdata_xwiki_link_wtr implements Bry_fmtr_arg { public Wdata_xwiki_link_wtr Page_(Xoa_page page) {this.page = page; return this;} private Xoa_page page; public void XferAry(Bry_bfr bfr, int idx) { - ListAdp langs = page.Xwiki_langs(); - byte[] qid = Write_wdata_links(langs, page.Wiki(), page.Ttl(), page.Wdata_external_lang_links()); - int langs_len = langs.Count(); - if (langs_len > 0) - page.Wiki().Xwiki_mgr().Lang_mgr().Html_bld(bfr, page.Wiki(), langs, qid); + ListAdp slink_list = page.Slink_list(); + byte[] qid = Write_wdata_links(slink_list, page.Wiki(), page.Ttl(), page.Wdata_external_lang_links()); + int slink_list_len = slink_list.Count(); + if (slink_list_len > 0) + page.Wiki().Xwiki_mgr().Lang_mgr().Html_bld(bfr, page.Wiki(), slink_list, qid); } - public static byte[] Write_wdata_links(ListAdp langs, Xow_wiki wiki, Xoa_ttl ttl, Wdata_external_lang_links_data external_links_mgr) { + public static byte[] Write_wdata_links(ListAdp slink_list, Xow_wiki wiki, Xoa_ttl ttl, Wdata_external_lang_links_data external_links_mgr) { try { switch (wiki.Domain_tid()) { case Xow_wiki_domain_.Tid_home: // home will never be in wikidata @@ -41,8 +41,8 @@ public class Wdata_xwiki_link_wtr implements Bry_fmtr_arg { Xow_wiki_abrv wiki_abrv = new Xow_wiki_abrv(); int len = links.Count(); for (int i = 0; i < len; i++) { - Wdata_sitelink_itm sitelink = (Wdata_sitelink_itm)links.FetchAt(i); - byte[] xwiki_key = sitelink.Site(); + Wdata_sitelink_itm slink = (Wdata_sitelink_itm)links.FetchAt(i); + byte[] xwiki_key = slink.Site(); Xow_wiki_abrv_.parse_(wiki_abrv, xwiki_key, 0, xwiki_key.length); if (wiki_abrv.Domain_tid() == Xow_wiki_abrv_.Tid_null) { wiki.App().Usr_dlg().Warn_many("", "", "unknown wiki in wikidata: ttl=~{0} wiki=~{1}", ttl.Page_db_as_str(), String_.new_utf8_(xwiki_key)); @@ -53,18 +53,19 @@ public class Wdata_xwiki_link_wtr implements Bry_fmtr_arg { if (external_links_mgr_enabled && external_links_mgr.Langs_hide(lang_key, 0, lang_key.length)) continue; tmp_bfr.Add(lang_key); tmp_bfr.Add_byte(Byte_ascii.Colon); - tmp_bfr.Add(sitelink.Name()); - Xoa_ttl lang_ttl = Xoa_ttl.parse_(wiki, tmp_bfr.Xto_bry_and_clear()); - if (lang_ttl == null) continue; // invalid ttl - Xow_xwiki_itm xwiki_itm = lang_ttl.Wik_itm(); + tmp_bfr.Add(slink.Name()); + Xoa_ttl slink_ttl = Xoa_ttl.parse_(wiki, tmp_bfr.Xto_bry_and_clear()); + if (slink_ttl == null) continue; // invalid ttl + Xow_xwiki_itm xwiki_itm = slink_ttl.Wik_itm(); if ( xwiki_itm == null // not a known xwiki; EX: [[zzz:abc]] || Bry_.Eq(xwiki_itm.Domain(), wiki.Domain_bry()) // skip if same as self; i.e.: do not include links to enwiki if already in enwiki ) continue; - langs.Add(lang_ttl); + slink.Page_ttl_(slink_ttl); + slink_list.Add(slink); } tmp_bfr.Mkr_rls(); if (external_links_mgr_enabled && external_links_mgr.Sort()) - langs.SortBy(Xoa_ttl_sorter._); + slink_list.SortBy(Xoa_ttl_sorter._); return doc.Qid(); } catch (Exception e) {Err_.Noop(e); return Qid_null;} } diff --git a/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_xwiki_link_wtr_tst.java b/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_xwiki_link_wtr_tst.java index 485b1570d..dcd660c61 100644 --- a/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_xwiki_link_wtr_tst.java +++ b/400_xowa/src/gplx/xowa/xtns/wdatas/Wdata_xwiki_link_wtr_tst.java @@ -39,7 +39,7 @@ public class Wdata_xwiki_link_wtr_tst { , "

grp1

" , " " , " " - , " " + , " " , " " , "
GermanQ1 deGerman
  • Q1 de
  • " , "
    " @@ -77,6 +77,26 @@ public class Wdata_xwiki_link_wtr_tst { fxt.Init_pages_add(wdata_doc); fxt.Test_xwiki_links("Q1_en", "q1_de", "q1_fr"); } + @Test public void Badges() { + fxt.Init_xwikis_add("de", "fr"); + fxt.Init_qids_add("en", Xow_wiki_domain_.Tid_wikipedia, "Q1_en", "Q1"); + fxt.Init_pages_add(fxt.Wdoc_bldr("Q1").Add_sitelink("enwiki", "Q1_en").Add_sitelink("dewiki", "Q1_de", "Q17437796").Add_sitelink("frwiki", "Q1_fr", "Q17437798").Xto_wdoc()); + fxt.Test_parse_langs("", String_.Concat_lines_nl + ( "
    " + , "
    In other languages (wikidata)
    " + , " " + , "
    " + )); + } + // @Test public void No_wikidata_link() { // fxt.Init_xwikis_add("fr", "de"); // fxt.Test_parse_langs("[[fr:A]]", String_.Concat_lines_nl diff --git a/400_xowa/src/gplx/xowa/xtns/wdatas/core/Wdata_sitelink_itm.java b/400_xowa/src/gplx/xowa/xtns/wdatas/core/Wdata_sitelink_itm.java index e6ec721b9..d1dedaf10 100644 --- a/400_xowa/src/gplx/xowa/xtns/wdatas/core/Wdata_sitelink_itm.java +++ b/400_xowa/src/gplx/xowa/xtns/wdatas/core/Wdata_sitelink_itm.java @@ -26,6 +26,7 @@ public class Wdata_sitelink_itm implements Wdata_lang_sortable { public byte[] Lang_code() {return lang;} public int Lang_sort() {return lang_sort;} public void Lang_sort_(int v) {lang_sort = v;} private int lang_sort = Wdata_lang_sorter.Sort_null; public Xow_wiki_domain Domain_info() {if (domain_info == null) domain_info = Xow_wiki_alias.parse_by_wmf_key(site); return domain_info;} private Xow_wiki_domain domain_info; + public Xoa_ttl Page_ttl() {return page_ttl;} public Wdata_sitelink_itm Page_ttl_(Xoa_ttl v) {page_ttl = v; return this;} private Xoa_ttl page_ttl; // PERF: cache title to avoid creating new Object for "In Other langs"; DATE:2014-10-20 @Override public String toString() {// TEST: return String_.Concat_with_str("|", String_.new_utf8_(site), String_.new_utf8_(name), String_.Concat_with_str(",", String_.Ary(badges))); } diff --git a/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_grp.java b/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_grp.java index f50b06c4a..1e1589c0d 100644 --- a/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_grp.java +++ b/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_grp.java @@ -32,13 +32,13 @@ public class Xow_lang_grp implements GfoInvkAble { Xow_lang_itm[] itms_ary = this.Itms(); int itms_len = itms_ary.length; for (int i = 0; i < itms_len; i++) - itms_ary[i].Atrs_set(null, false); // clear out pre-existing page names; needed b/c this struct is a singleton for entire wiki + itms_ary[i].Atrs_set(null, false, null); // clear out pre-existing page names; needed b/c this struct is a singleton for entire wiki itms_active_len = 0; } public Bry_fmtr Html_all() {return html_all;} Bry_fmtr html_all; public Xow_lang_grp Html_all_(String s) {html_all = Bry_fmtr.new_(s, "all_name", "grps"); return this;} public byte[] Html_grp_bgn() {return html_grp_bgn;} private byte[] html_grp_bgn = Bry_.new_ascii_("\n "); public byte[] Html_grp_end() {return html_grp_end;} private byte[] html_grp_end = Bry_.new_ascii_("\n "); - public Bry_fmtr Html_itm() {return html_itm;} Bry_fmtr html_itm; public Xow_lang_grp Html_itm_(String s) {html_itm = Bry_fmtr.new_(s, "lang_code", "lang_domain", "lang_name", "lang_href", "pagename_translation"); return this;} + public Bry_fmtr Html_itm() {return html_itm;} Bry_fmtr html_itm; public Xow_lang_grp Html_itm_(String s) {html_itm = Bry_fmtr.new_(s, "lang_code", "lang_domain", "lang_name", "lang_href", "pagename_translation", "page_badge"); return this;} public void Html_bld(Bry_bfr bfr, Xow_wiki wiki) { Xow_lang_itm[] itms_ary = this.Itms(); if (sort_mode == Xow_lang_grp.Sort_mode_page_name) @@ -62,15 +62,15 @@ public class Xow_lang_grp implements GfoInvkAble { Xow_lang_grp rv = new Xow_lang_grp(); rv.lang_mgr = lang_mgr; rv.id = id; rv.key = key; rv.name = key; rv.Html_all_(String_.Concat_lines_nl_skip_last - ( "" - , "

    ~{all_name}

    " - , " ~{grps}" - , "
    " - )); + ( "" + , "

    ~{all_name}

    " + , " ~{grps}" + , "
    " + )); rv.Html_itm_(String_.Concat_lines_nl_skip_last - ( "" - , " ~{lang_name}~{pagename_translation}" - )); + ( "" + , " ~{lang_name}~{pagename_translation}" + )); return rv; } private Xow_lang_grp() {} Xow_lang_mgr lang_mgr; diff --git a/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_itm.java b/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_itm.java index aa2de5769..6d50026a1 100644 --- a/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_itm.java +++ b/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_itm.java @@ -27,11 +27,12 @@ public class Xow_lang_itm { public byte[] Page_name() {return page_name;} private byte[] page_name; public boolean Page_name_has() {return Bry_.Len_gt_0(page_name);} public boolean Empty_xwiki() {return empty_xwiki;} private boolean empty_xwiki; + public byte[][] Page_badges() {return page_badges;} private byte[][] page_badges; public void Html_bld(Bry_bfr bfr, Xow_wiki wiki) { html_grp.Html_itm().Bld_bfr(bfr, lang.Key_bry(), xwiki.Domain(), lang.Local_name_bry(), page_name); } - public void Atrs_set(byte[] page_name, boolean empty_xwiki) { - this.page_name = page_name; this.empty_xwiki = empty_xwiki; + public void Atrs_set(byte[] page_name, boolean empty_xwiki, byte[][] page_badges) { + this.page_name = page_name; this.empty_xwiki = empty_xwiki; this.page_badges = page_badges; html_grp.Itms_active_len_add_one_(); } } diff --git a/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr.java b/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr.java index 7c2f25975..7079b7e70 100644 --- a/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr.java +++ b/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr.java @@ -16,7 +16,7 @@ You should have received a copy of the GNU Affero General Public License along with this program. If not, see . */ package gplx.xowa; import gplx.*; -import gplx.xowa.wikis.xwikis.*; import gplx.xowa.apis.xowa.html.*; +import gplx.xowa.wikis.xwikis.*; import gplx.xowa.apis.xowa.html.*; import gplx.xowa.xtns.wdatas.core.*; public class Xow_lang_mgr { Xow_lang_mgr() { int len = Xol_lang_itm_.Id__max; @@ -67,15 +67,16 @@ public class Xow_lang_mgr { else return GfoInvkAble_.Rv_unhandled; return this; } private static final String Invk_get = "get", Invk_sort = "sort"; - public void Html_bld(Bry_bfr bfr, Xow_wiki wiki, ListAdp ttl_list, byte[] qid) { + public void Html_bld(Bry_bfr bfr, Xow_wiki wiki, ListAdp slink_list, byte[] qid) { int grp_len = hash.Count(); for (int i = 0; i < grp_len; i++) { Xow_lang_grp grp = (Xow_lang_grp)hash.FetchAt(i); grp.Itms_reset(); } - int ttl_list_len = ttl_list.Count(); - for (int i = 0; i < ttl_list_len; i++) { - Xoa_ttl ttl = (Xoa_ttl)ttl_list.FetchAt(i); + int slink_len = slink_list.Count(); + for (int i = 0; i < slink_len; i++) { + Wdata_sitelink_itm slink = (Wdata_sitelink_itm)slink_list.FetchAt(i); + Xoa_ttl ttl = slink.Page_ttl(); Xow_xwiki_itm xwiki = ttl.Wik_itm(); int lang_id = xwiki.Lang_id(); Xow_lang_itm itm = itms[lang_id]; // NOTE: handles ttls like [[fr:]] and [[:fr;]] which have an empty Page_txt, but a valued Full_txt_raw @@ -85,9 +86,9 @@ public class Xow_lang_mgr { ttl_bry = wiki.Ctx().Cur_page().Ttl().Page_txt(); empty_xwiki = true; } - itm.Atrs_set(ttl_bry, empty_xwiki); + itm.Atrs_set(ttl_bry, empty_xwiki, slink.Badges()); } - html_bldr.Init(this, wiki, ttl_list, ttl_list_len, qid); + html_bldr.Init(this, wiki, slink_list, slink_len, qid); html_bldr.XferAry(bfr, -1); } private Xow_lang_itm[] itms = null; Xow_lang_html html_bldr = new Xow_lang_html(); public static Xow_lang_mgr dflt_() { @@ -139,12 +140,13 @@ class Xow_lang_html implements Bry_fmtr_arg { byte[] domain = itm.Lang_domain(); byte[] page_name = itm.Page_name(); byte[] local_name = itm.Lang_name(); + byte[] badge_cls = Badge_cls(tmp_bfr, itm.Page_badges()); if (wiki.App().User().Wiki().Xwiki_mgr().Get_by_key(domain) == null) tmp_bfr.Add(Xoh_href_parser.Href_http_bry).Add(domain).Add(Xoh_href_parser.Href_wiki_bry); else tmp_bfr.Add(Xoh_href_parser.Href_site_bry).Add(domain).Add(Xoh_href_parser.Href_wiki_bry); if (!itm.Empty_xwiki()) tmp_bfr.Add(page_name); - grp.Html_itm().Bld_bfr_many(bfr, lang_key, domain, local_name, tmp_bfr.Xto_bry_and_clear(), page_name); + grp.Html_itm().Bld_bfr_many(bfr, lang_key, domain, local_name, tmp_bfr.Xto_bry_and_clear(), page_name, badge_cls); ++grp_counter; if (grp_counter == 3) { row_opened = false; @@ -160,4 +162,30 @@ class Xow_lang_html implements Bry_fmtr_arg { break; } } private Xow_lang_grp grp; Bry_bfr tmp_bfr = Bry_bfr.reset_(255); + private static byte[] Badge_cls(Bry_bfr bfr, byte[][] badges) { + if (badges == null) badges = Bry_.Ary_empty; + int badges_len = badges.length; + bfr.Add(Cls_bgn); + if (badges_len == 0) + bfr.Add(Badge_none_cls); + else { + for (int i = 0; i < badges_len; ++i) { + if (i != 0) bfr.Add_byte_comma(); + byte[] badge = badges[i]; + if (Bry_.Eq(badge, Badge_good_qid)) bfr.Add(Badge_good_cls); + else if (Bry_.Eq(badge, Badge_feat_qid)) bfr.Add(Badge_feat_cls); + else Gfo_usr_dlg_._.Warn_many("", "", "unknown badge: badge~{0}", String_.new_utf8_(badge)); + } + } + bfr.Add_byte_apos(); + return bfr.Xto_bry_and_clear(); + } + private static final byte[] + Badge_good_qid = Bry_.new_ascii_("Q17437798") + , Badge_good_cls = Bry_.new_ascii_("badge-goodarticle") + , Badge_feat_qid = Bry_.new_ascii_("Q17437796") + , Badge_feat_cls = Bry_.new_ascii_("badge-featuredarticle") + , Badge_none_cls = Bry_.new_ascii_("badge-none") + , Cls_bgn = Bry_.new_ascii_(" class='") + ; } \ No newline at end of file diff --git a/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr_fxt.java b/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr_fxt.java index 732289ebd..e1b69f20d 100644 --- a/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr_fxt.java +++ b/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr_fxt.java @@ -59,7 +59,7 @@ public class Xow_lang_mgr_fxt { wiki.Html_mgr().Html_wtr().Write_all(bfr, ctx, raw_bry, root); Bry_bfr html_bfr = Bry_bfr.new_(); - wiki.Xwiki_mgr().Lang_mgr().Html_bld(html_bfr, wiki, ctx.Cur_page().Xwiki_langs(), gplx.xowa.xtns.wdatas.Wdata_xwiki_link_wtr.Qid_null); + wiki.Xwiki_mgr().Lang_mgr().Html_bld(html_bfr, wiki, ctx.Cur_page().Slink_list(), gplx.xowa.xtns.wdatas.Wdata_xwiki_link_wtr.Qid_null); Tfds.Eq_str_lines(expd, html_bfr.Xto_str_and_clear()); } } diff --git a/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr_tst.java b/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr_tst.java index 754017862..691b6e04c 100644 --- a/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr_tst.java +++ b/400_xowa/src_120_wiki/gplx/xowa/Xow_lang_mgr_tst.java @@ -18,7 +18,7 @@ along with this program. If not, see . package gplx.xowa; import gplx.*; import org.junit.*; public class Xow_lang_mgr_tst { - Xow_lang_mgr_fxt fxt = new Xow_lang_mgr_fxt(); + private Xow_lang_mgr_fxt fxt = new Xow_lang_mgr_fxt(); @Before public void init() {fxt.Clear();} @Test public void Basic() { fxt.tst("[[simple:Earth]] [[fr:Terre]] [[es:Tierra]] [[de:Erde]] [[it:Terre]]", String_.Concat_lines_nl_skip_last @@ -28,16 +28,16 @@ public class Xow_lang_mgr_tst { , "

    grp1

    " , " " , " " - , " " - , " " - , " " + , " " + , " " + , " " , " " , "
    SimpleEarthSpanishTierraItalianTerreSimple
  • Earth
  • Spanish
  • Tierra
  • Italian
  • Terre
  • " , "

    grp2

    " , " " , " " - , " " - , " " + , " " + , " " , " " , "
    FrenchTerreGermanErdeFrench
  • Terre
  • German
  • Erde
  • " , " " @@ -52,7 +52,7 @@ public class Xow_lang_mgr_tst { , "

    grp1

    " , " " , " " - , " " + , " " , " " , "
    SimpleTest pageSimple
  • Test page
  • " , " " @@ -68,7 +68,7 @@ public class Xow_lang_mgr_tst { , "

    grp1

    " , " " , " " - , " " + , " " , " " , "
    ChineseEarthChinese
  • Earth
  • " , " " @@ -83,7 +83,7 @@ public class Xow_lang_mgr_tst { , "

    grp1

    " , " " , " " - , " " + , " " , " " , "
    SimpleA#bSimple
  • A#b
  • " , " " diff --git a/400_xowa/src_162_xfer/gplx/xowa/Xof_xfer_queue.java b/400_xowa/src_162_xfer/gplx/xowa/Xof_xfer_queue.java index 3373123d7..dac907046 100644 --- a/400_xowa/src_162_xfer/gplx/xowa/Xof_xfer_queue.java +++ b/400_xowa/src_162_xfer/gplx/xowa/Xof_xfer_queue.java @@ -81,6 +81,7 @@ public class Xof_xfer_queue { fsdb_itm.Html_img_wkr_(xfer_itm.Html_img_wkr()); rv.Add(fsdb_itm); } + this.Clear(); return rv; } private static final String GRP_KEY = "xowa.xfer.queue"; diff --git a/400_xowa/src_300_html/gplx/xowa/Xoa_page.java b/400_xowa/src_300_html/gplx/xowa/Xoa_page.java index 1980faa86..114cbea66 100644 --- a/400_xowa/src_300_html/gplx/xowa/Xoa_page.java +++ b/400_xowa/src_300_html/gplx/xowa/Xoa_page.java @@ -32,7 +32,7 @@ public class Xoa_page { public Xoa_app App() {return app;} private Xoa_app app; public Xow_wiki Wiki() {return wiki;} private Xow_wiki wiki; public Xol_lang Lang() {return lang;} public Xoa_page Lang_(Xol_lang v) {lang = v; return this;} private Xol_lang lang; - public Xoa_revision_data Revision_data() {return revision_data;} private Xoa_revision_data revision_data = new Xoa_revision_data(); + public Xopg_revision_data Revision_data() {return rev_data;} private Xopg_revision_data rev_data = new Xopg_revision_data(); public Xopg_html_data Html_data() {return html_data;} private Xopg_html_data html_data = new Xopg_html_data(); public Xoa_ttl Ttl() {return ttl;} public Xoa_page Ttl_(Xoa_ttl v) {ttl = v; url.Wiki_bry_(wiki.Domain_bry()).Page_bry_(v.Full_url()); return this;} private Xoa_ttl ttl; public Xoa_url Url() {return url;} public Xoa_page Url_(Xoa_url v) {url = v; return this;} private Xoa_url url = Xoa_url.blank_(); @@ -56,7 +56,7 @@ public class Xoa_page { public Xop_lnki_logger_redlinks_mgr Lnki_redlinks_mgr() {return lnki_redlinks_mgr;} private Xop_lnki_logger_redlinks_mgr lnki_redlinks_mgr; public Ref_itm_mgr Ref_mgr() {return ref_mgr;} private Ref_itm_mgr ref_mgr = new Ref_itm_mgr(); public Xopg_popup_mgr Popup_mgr() {return popup_mgr;} private Xopg_popup_mgr popup_mgr = new Xopg_popup_mgr(); - public ListAdp Xwiki_langs() {return xwiki_langs;} private ListAdp xwiki_langs = ListAdp_.new_(); + public ListAdp Slink_list() {return slink_list;} private ListAdp slink_list = ListAdp_.new_(); public Wdata_external_lang_links_data Wdata_external_lang_links() {return wdata_external_lang_links;} private Wdata_external_lang_links_data wdata_external_lang_links = new Wdata_external_lang_links_data(); public boolean Pages_recursed() {return pages_recursed;} public void Pages_recursed_(boolean v) {pages_recursed = v; } private boolean pages_recursed; public Xopg_tmpl_prepend_mgr Tmpl_prepend_mgr() {return tmpl_prepend_mgr;} private Xopg_tmpl_prepend_mgr tmpl_prepend_mgr = new Xopg_tmpl_prepend_mgr(); @@ -84,14 +84,14 @@ public class Xoa_page { hdump_data.Clear(); wdata_external_lang_links.Reset(); gplx.xowa.xtns.scribunto.Scrib_core.Core_page_changed(this); - xwiki_langs.Clear(); + slink_list.Clear(); html_data.Clear(); lnki_file_mgr.Clear(); pages_recursed = false; tmpl_stack_ary = Bry_.Ary_empty; tmpl_stack_ary_len = tmpl_stack_ary_max = 0; popup_mgr.Clear(); - revision_data.Clear(); + rev_data.Clear(); tmpl_prepend_mgr.Clear(); } public static final Xoa_page Empty = new Xoa_page().Missing_(); diff --git a/400_xowa/src_300_html/gplx/xowa/Xoa_revision_data.java b/400_xowa/src_300_html/gplx/xowa/Xoa_revision_data.java deleted file mode 100644 index 35266be31..000000000 --- a/400_xowa/src_300_html/gplx/xowa/Xoa_revision_data.java +++ /dev/null @@ -1,27 +0,0 @@ -/* -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 . -*/ -package gplx.xowa; import gplx.*; -public class Xoa_revision_data { - public int Id() {return id;} public Xoa_revision_data Id_(int v) {id = v; return this;} private int id; - public DateAdp Modified_on() {return modified_on;} public Xoa_revision_data Modified_on_(DateAdp v) {modified_on = v; return this;} private DateAdp modified_on = DateAdp_.MinValue; - public byte[] User() {return user;} public Xoa_revision_data User_(byte[] v) {user = v; return this;} private byte[] user = Bry_.Empty; - public byte[] Protection_level() {return protection_level;} public Xoa_revision_data Protection_level_(byte[] v) {protection_level = v; return this;} private byte[] protection_level = Bry_.Empty; - public int Html_db_id() {return html_db_id;} public void Html_db_id_(int v) {html_db_id = v;} private int html_db_id = -1; - public void Clear() {// NOTE: do not clear data b/c saving in Edit will call clear and id will be reset to 0 - } -} diff --git a/400_xowa/src_310_url/gplx/xowa/Xoh_href_parser.java b/400_xowa/src_310_url/gplx/xowa/Xoh_href_parser.java index 9eb2357e8..b6d44b39e 100644 --- a/400_xowa/src_310_url/gplx/xowa/Xoh_href_parser.java +++ b/400_xowa/src_310_url/gplx/xowa/Xoh_href_parser.java @@ -56,10 +56,10 @@ public class Xoh_href_parser { rv.Tid_(Xoh_href.Tid_anchor); rv.Wiki_(wiki.Domain_bry()); // wiki is always current rv.Page_(cur_page); // page is always current - rv.Anchor_(Bry_.Mid(raw, file_slash_end + 1, raw_len)); // +1 to skip #; i.e. Anchor should be "A" not "#A" + rv.Anchor_(Bry_.Mid(raw, file_slash_end + 1, raw_len)); // +1 to skip #; i.e. Anchor should be "A" not "#A" return; } - Object seg_obj = segs.Match_bgn(raw, bgn, raw_len); // match /wiki/ or /site/ or /xcmd/ + Object seg_obj = segs.Match_bgn(raw, bgn, raw_len); // match /wiki/ or /site/ or /xcmd/ if (seg_obj == null) // nothing matched; assume file; EX: file:///C/dir/fil.txt -> /C/dir/fil.txt rv.Tid_(Xoh_href.Tid_file); else { // something matched; @@ -144,7 +144,7 @@ public class Xoh_href_parser { rv.Wiki_(ttl.Wik_itm().Domain()); // wiki is the xwiki prefix; EX: "en.wikpedia.org//wiki/fr:A" -> "fr.wikpedia.org/wiki/A" } byte[] page_bry = encoder.Decode(ttl.Full_txt()); // note that Full is everything except for ns, so it handles "fr:A" ("fr:" being treated as ns, so only "A" will be Full_txt) - if (Bry_.Len_eq_0(page_bry)) // handle xwiki hrefs like "fr:"; EX: "/wiki/wikipedia:" on en.wikisource.org/Main Page + if (Bry_.Len_eq_0(page_bry)) // handle xwiki hrefs like "fr:"; EX: "/wiki/wikipedia:" on en.wikisource.org/Main Page page_bry = Xoa_page_.Main_page_bry_empty; // if (ttl.Qarg_bgn() != Bry_.NotFound) // rv.Qarg_(ttl.Qarg_txt()); @@ -163,9 +163,9 @@ public class Xoh_href_parser { rv.Wiki_(wiki_bry); int page_pos = slash + Href_wiki_len; byte[] page_bry = page_pos < len - ? Bry_.Mid(raw, page_pos, len) // page is text after next "/" + "/wiki/"; + ? Bry_.Mid(raw, page_pos, len) // page is text after next "/" + "/wiki/"; : Bry_.Empty; - if (Bry_.Len_eq_0(page_bry)) // handle "/site/fr.wikipedia.org/wiki/"; note that these are generated by [[fr:]] + if (Bry_.Len_eq_0(page_bry)) // handle "/site/fr.wikipedia.org/wiki/"; note that these are generated by [[fr:]] page_bry = wiki.Props().Main_page(); // default to Main Page // int qarg_pos = Bry_finder.Find_bwd(page_bry, Byte_ascii.Question); // byte[] qarg_bry = null; diff --git a/400_xowa/src_440_lnki/gplx/xowa/Xop_lnki_wkr__xwiki_tst.java b/400_xowa/src_440_lnki/gplx/xowa/Xop_lnki_wkr__xwiki_tst.java index 4eeedb256..e98acd6ad 100644 --- a/400_xowa/src_440_lnki/gplx/xowa/Xop_lnki_wkr__xwiki_tst.java +++ b/400_xowa/src_440_lnki/gplx/xowa/Xop_lnki_wkr__xwiki_tst.java @@ -63,7 +63,7 @@ public class Xop_lnki_wkr__xwiki_tst { ( "[[:fr:A]]", String_.Concat_lines_nl_skip_last ( "A" )); - Tfds.Eq(0, fxt.Page().Xwiki_langs().Count()); + Tfds.Eq(0, fxt.Page().Slink_list().Count()); } @Test public void Simple_and_english() { // PURPOSE: s.w xwiki links to en were not working b/c s.w and en had same super lang of English; PAGE:s.q:Anonymous DATE:2014-09-10 Xoa_app app = Xoa_app_fxt.app_(); @@ -74,7 +74,7 @@ public class Xop_lnki_wkr__xwiki_tst { ( "[[en:A]]" , "" ); - Tfds.Eq(1, fxt.Page().Xwiki_langs().Count()); // test 1 xwiki lang + Tfds.Eq(1, fxt.Page().Slink_list().Count()); // test 1 xwiki lang } @Test public void Species_and_commons() { // PURPOSE: species xwiki links to commons should not put link in wikidata langs; PAGE:species:Scarabaeidae DATE:2014-09-10 Xoa_app app = Xoa_app_fxt.app_(); @@ -85,7 +85,7 @@ public class Xop_lnki_wkr__xwiki_tst { ( "[[commons:A]]" , "commons:A" ); - Tfds.Eq(0, fxt.Page().Xwiki_langs().Count()); // no xwiki langs + Tfds.Eq(0, fxt.Page().Slink_list().Count()); // no xwiki langs } @Test public void Wiktionary_and_wikipedia() { // PURPOSE: do not create xwiki links if same lang and differet type; PAGE:s.d:water DATE:2014-09-14 Xoa_app app = Xoa_app_fxt.app_(); @@ -96,7 +96,7 @@ public class Xop_lnki_wkr__xwiki_tst { ( "[[w:A]]" , "w:A" ); - Tfds.Eq(0, fxt.Page().Xwiki_langs().Count()); // test 0 xwiki lang + Tfds.Eq(0, fxt.Page().Slink_list().Count()); // test 0 xwiki lang } @Test public void Species_and_wikipedia() { // PURPOSE: species creates xwiki links to wikipedia; PAGE:species:Puccinia DATE:2014-09-14 Xoa_app app = Xoa_app_fxt.app_(); @@ -107,7 +107,7 @@ public class Xop_lnki_wkr__xwiki_tst { ( "[[fr:A]]" , "" ); - Tfds.Eq(1, fxt.Page().Xwiki_langs().Count()); // 1 xwiki lang + Tfds.Eq(1, fxt.Page().Slink_list().Count()); // 1 xwiki lang } private void Reg_xwiki_alias(String alias, String domain) { Xop_fxt.Reg_xwiki_alias(fxt.Wiki(), alias, domain); diff --git a/400_xowa/src_490_xnde/gplx/xowa/Xop_xnde_wkr.java b/400_xowa/src_490_xnde/gplx/xowa/Xop_xnde_wkr.java index a48a08f84..af0a5aa3f 100644 --- a/400_xowa/src_490_xnde/gplx/xowa/Xop_xnde_wkr.java +++ b/400_xowa/src_490_xnde/gplx/xowa/Xop_xnde_wkr.java @@ -103,9 +103,9 @@ public class Xop_xnde_wkr implements Xop_ctx_wkr { } if (tag_obj == null) { // not a known xml tag; EX: ""; "if 5 < 7 then" if (ctx.Parse_tid() == Xop_parser_.Parse_tid_page_wiki) { - if (ctx_cur_tid_is_tblw_atr_owner) // to be ; EX: w:Exchange_value fxt.Init_log_(Xop_xnde_log.No_inline); fxt.Test_parse_page_all_str("", ""); @@ -66,4 +66,9 @@ public class Xop_xnde_wkr__err_malformed_tst { , "" )); } + @Test public void Incomplete_tag() { // PURPOSE: handle incomplete tag sequences; DATE:2014-10-22 + fxt.Test_parse_page_all_str("<", "<"); + fxt.Test_parse_page_all_str(">{{{1}}}"); fxt.Test_parse_page_all_str ( "{{pre2|a}}" diff --git a/400_xowa/src_500_tmpl/gplx/xowa/Xop_subst_tst.java b/400_xowa/src_500_tmpl/gplx/xowa/Xop_subst_tst.java index b25975a79..d472ae12c 100644 --- a/400_xowa/src_500_tmpl/gplx/xowa/Xop_subst_tst.java +++ b/400_xowa/src_500_tmpl/gplx/xowa/Xop_subst_tst.java @@ -65,10 +65,15 @@ public class Xop_subst_tst { fxt.Init_log_(Xop_ttl_log.Invalid_char); fxt.Test_parse_page_tmpl_str("{{test|Template:[xyz]}}", "%7B%7BTemplate%3ATemplate%3A%5Bxyz%5D%7D%7D"); // url-encoded version of {{safesubst:Template:xyz}} } + @Test public void Nowiki() { // PURPOSE: stack overflow; PAGE:Близкие_друзья_(Сезон_2) DATE:2014-10-21 + fxt.Init_defn_add("ET", ""); + fxt.Init_defn_add("ds", "{{subst:ET|{{subst:ds}}}}"); + fxt.Test_parse_page_tmpl_str("{{subst:ds}}", ""); // {{subst:ds}} causes stack overflow; {{ds}} does not + } // NOTE: these are actually not good tests; MW does subst just before save; it doesn't do subst on load; in this case, the tests are testing load (which will noop); they need to test save (which xowa doesn't do) -// @Test public void Tmpl_txt_subst() {fxt.Test_parse_tmpl_str_test("{{subst:xo_print|a}}" , "{{test}}" , "a");} -// @Test public void Tmpl_txt_subst_prm() {fxt.Test_parse_tmpl_str_test("{{subst:xo_print|{{{1}}}}}" , "{{test|a}}" , "a");} + // @Test public void Tmpl_txt_subst() {fxt.Test_parse_tmpl_str_test("{{subst:xo_print|a}}" , "{{test}}" , "a");} + // @Test public void Tmpl_txt_subst_prm() {fxt.Test_parse_tmpl_str_test("{{subst:xo_print|{{{1}}}}}" , "{{test|a}}" , "a");} //@Test public void Tmpl_txt_safesubst_prm() {fxt.Test_parse_tmpl_str_test("{{{{{|safesubst:}}}ns:Category}}" , "{{test}}" , "Category");} //@Test public void Tmpl_txt_subst_immed() {fxt.Test_parse_tmpl_str_test("{{xo_print{{subst:!}}a}}" , "{{test}}" , "a");} diff --git a/400_xowa/src_500_tmpl/gplx/xowa/Xot_invk_tkn.java b/400_xowa/src_500_tmpl/gplx/xowa/Xot_invk_tkn.java index e3bf7c86a..fb3346a7e 100644 --- a/400_xowa/src_500_tmpl/gplx/xowa/Xot_invk_tkn.java +++ b/400_xowa/src_500_tmpl/gplx/xowa/Xot_invk_tkn.java @@ -67,7 +67,7 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk { name_ary_len = name_ary.length; name_bgn = Bry_finder.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| }} + || 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 return false; @@ -104,9 +104,8 @@ public class Xot_invk_tkn extends Xop_tkn_itm_base implements Xot_invk { bfr.Add(Xop_curly_bgn_lxr.Hook).Add(name_ary); for (int i = 0; i < args_len; i++) { Arg_nde_tkn nde = args[i]; - // bfr.Add_byte(Byte_ascii.Pipe); - Xot_fmtr_prm._.Write(Byte_ascii.Pipe); - nde.Tmpl_fmt(ctx, src, Xot_fmtr_prm._); + bfr.Add_byte(Byte_ascii.Pipe); // add | + bfr.Add_mid(src, nde.Src_bgn(), nde.Src_end()); // add entire arg; "k=v"; note that src must be added, not evaluated, else may be dropped and cause stack overflow; PAGE:ru.w:Близкие_друзья_(Сезон_2) DATE:2014-10-21 } Xot_fmtr_prm._.Print(bfr); bfr.Add(Xop_curly_end_lxr.Hook);