mirror of
https://github.com/gnosygnu/xowa.git
synced 2026-03-02 03:49:30 +00:00
uca category support and other changes
This commit is contained in:
22
400_xowa/src/gplx/core/intls/ucas/Uca_collator.java
Normal file
22
400_xowa/src/gplx/core/intls/ucas/Uca_collator.java
Normal file
@@ -0,0 +1,22 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.core.intls.ucas; import gplx.*; import gplx.core.*; import gplx.core.intls.*;
|
||||
public interface Uca_collator {
|
||||
void Init(String locale, boolean numeric_ordering);
|
||||
byte[] Get_sortkey(String s);
|
||||
}
|
||||
25
400_xowa/src/gplx/core/intls/ucas/Uca_collator_.java
Normal file
25
400_xowa/src/gplx/core/intls/ucas/Uca_collator_.java
Normal file
@@ -0,0 +1,25 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.core.intls.ucas; import gplx.*; import gplx.core.*; import gplx.core.intls.*;
|
||||
public class Uca_collator_ {
|
||||
public static Uca_collator New(String locale, boolean numeric_ordering) {
|
||||
Uca_collator rv = new Uca_collator__icu__4_8();
|
||||
rv.Init(locale, numeric_ordering);
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,49 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.core.intls.ucas; import gplx.*; import gplx.core.*; import gplx.core.intls.*;
|
||||
import java.util.Locale;
|
||||
import com.ibm.icu.text.CollationKey;
|
||||
import com.ibm.icu.text.Collator;
|
||||
import com.ibm.icu.text.RuleBasedCollator;
|
||||
class Uca_collator__icu__4_8 implements Uca_collator {
|
||||
private Collator collator;
|
||||
public void Init(String locale, boolean numeric_ordering) {
|
||||
try {
|
||||
this.collator = Collator.getInstance(Locale.forLanguageTag(locale));
|
||||
if (numeric_ordering) {
|
||||
RuleBasedCollator rbc = (RuleBasedCollator)collator;
|
||||
rbc.setNumericCollation(true);
|
||||
}
|
||||
} catch (Exception e) {throw Err_.new_wo_type("collator init failed", "err", Err_.Message_lang(e));}
|
||||
}
|
||||
public byte[] Get_sortkey(String s) {
|
||||
CollationKey key = collator.getCollationKey(s);
|
||||
byte[] src = key.toByteArray();
|
||||
int src_len = src.length;
|
||||
byte[] rv = src;
|
||||
|
||||
// remove last byte if it is 0 (which it often is)
|
||||
if (src_len > 0 && src[src_len - 1] == 0) {
|
||||
int rv_len = src_len - 1;
|
||||
rv = new byte[rv_len];
|
||||
for (int i = 0; i < rv_len; ++i)
|
||||
rv[i] = src[i];
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
51
400_xowa/src/gplx/core/intls/ucas/Uca_ltr_extractor.java
Normal file
51
400_xowa/src/gplx/core/intls/ucas/Uca_ltr_extractor.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.core.intls.ucas; import gplx.*; import gplx.core.*; import gplx.core.intls.*;
|
||||
public class Uca_ltr_extractor {
|
||||
private final boolean numeric;
|
||||
private final byte[] numeric_heading;
|
||||
private final Hash_adp_bry numeric_hash;
|
||||
public Uca_ltr_extractor(boolean numeric) {
|
||||
this.numeric = numeric;
|
||||
if (numeric) {
|
||||
numeric_heading = Bry_.new_a7("0-9");
|
||||
|
||||
// create hash of "0", "1", "2", ...
|
||||
numeric_hash = Hash_adp_bry.cs();
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
byte[] digit_bry = Bry_.new_by_int(Byte_ascii.Num_0 + i);
|
||||
numeric_hash.Add(digit_bry, digit_bry);
|
||||
}
|
||||
}
|
||||
else {
|
||||
numeric_heading = null;
|
||||
numeric_hash = null;
|
||||
}
|
||||
}
|
||||
public byte[] Get_1st_ltr(byte[] bry) {
|
||||
// NOTE: this is simplified and only does numeric logic; MW code loads up all ICU chars via first-letters-root.ser, adds custom chars, sorts them, and then does a binary search to find it; REF:IcuCollation.php!getFirstLetter
|
||||
int bry_len = bry.length;
|
||||
if (bry_len == 0) return Bry_.Empty;
|
||||
byte[] rv = gplx.core.intls.Utf8_.Get_char_at_pos_as_bry(bry, 0);
|
||||
if (numeric) {
|
||||
if (numeric_hash.Has(rv))
|
||||
rv = numeric_heading;
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
@@ -22,7 +22,7 @@ public class Io_buffer_rdr_tst {
|
||||
Io_mgr.Instance.InitEngine_mem();
|
||||
fil = Io_url_.mem_fil_("mem/byteStreamRdr.txt");
|
||||
ini_Write("0123456789");
|
||||
rdr = Io_buffer_rdr.new_(Io_stream_rdr_.file_(fil), 4);
|
||||
rdr = Io_buffer_rdr.new_(Io_stream_rdr_.New__raw(fil), 4);
|
||||
} Io_buffer_rdr rdr; Io_url fil;
|
||||
@After public void teardown() {rdr.Rls();}
|
||||
@Test public void Bfr_load_all() {
|
||||
|
||||
@@ -23,7 +23,7 @@ public class Io_stream_rdr_process implements Io_stream_rdr {
|
||||
private InputStream stream_read;
|
||||
private String[] process_args;
|
||||
Io_stream_rdr_process(Io_url process_exe, Io_url stream_url, String[] process_args) {this.process_exe = process_exe; this.url = stream_url; this.process_args = process_args;}
|
||||
public byte Tid() {return Io_stream_.Tid_bzip2;} // for now, classify as bzip2; not sure if separate tid is necessary
|
||||
public byte Tid() {return Io_stream_tid_.Tid__bzip2;} // for now, classify as bzip2; not sure if separate tid is necessary
|
||||
public boolean Exists() {return this.Len() > 0;}
|
||||
public Io_url Url() {return url;} public Io_stream_rdr Url_(Io_url v) {url = v; return this;} private Io_url url;
|
||||
public long Len() {return len;} public Io_stream_rdr Len_(long v) {len = v; return this;} private long len;
|
||||
|
||||
@@ -18,16 +18,16 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
package gplx.core.ios; import gplx.*; import gplx.core.*;
|
||||
import gplx.core.ios.streams.*;
|
||||
public class Io_stream_zip_mgr {
|
||||
private Io_stream_wtr wtr_gzip, wtr_zip, wtr_bzip2;
|
||||
private Io_stream_wtr wtr__gzip, wtr__zip, wtr__bzip2, wtr__xz;
|
||||
public byte[] Zip(byte type, byte[] val) {
|
||||
if (type == Io_stream_.Tid_raw) return val;
|
||||
if (type == Io_stream_tid_.Tid__raw) return val;
|
||||
Io_stream_wtr wtr = Wtr(type);
|
||||
wtr.Write(val, 0, val.length);
|
||||
wtr.Flush();
|
||||
return wtr.To_ary_and_clear();
|
||||
}
|
||||
public byte[] Unzip(byte type, byte[] val) {
|
||||
if (type == Io_stream_.Tid_raw) return val;
|
||||
if (type == Io_stream_tid_.Tid__raw) return val;
|
||||
Io_stream_rdr rdr = Rdr(type);
|
||||
rdr.Open_mem(val);
|
||||
return Io_stream_rdr_.Load_all_as_bry(Bry_bfr_.New(), rdr);
|
||||
@@ -35,20 +35,22 @@ public class Io_stream_zip_mgr {
|
||||
private Io_stream_wtr Wtr(byte type) {
|
||||
Bry_bfr bfr = Bry_bfr_.New();
|
||||
switch (type) {
|
||||
case Io_stream_.Tid_gzip : if (wtr_gzip == null) wtr_gzip = Io_stream_wtr_.new_by_mem(bfr, Io_stream_.Tid_gzip) ; return wtr_gzip.Open();
|
||||
case Io_stream_.Tid_zip : if (wtr_zip == null) wtr_zip = Io_stream_wtr_.new_by_mem(bfr, Io_stream_.Tid_zip) ; return wtr_zip.Open();
|
||||
case Io_stream_.Tid_bzip2 : if (wtr_bzip2 == null) wtr_bzip2 = Io_stream_wtr_.new_by_mem(bfr, Io_stream_.Tid_bzip2) ; return wtr_bzip2.Open();
|
||||
case Io_stream_.Tid_raw :
|
||||
default : throw Err_.new_unhandled(type);
|
||||
case Io_stream_tid_.Tid__gzip: if (wtr__gzip == null) wtr__gzip = Io_stream_wtr_.New_by_mem(bfr, Io_stream_tid_.Tid__gzip); return wtr__gzip.Open();
|
||||
case Io_stream_tid_.Tid__zip: if (wtr__zip == null) wtr__zip = Io_stream_wtr_.New_by_mem(bfr, Io_stream_tid_.Tid__zip); return wtr__zip.Open();
|
||||
case Io_stream_tid_.Tid__bzip2: if (wtr__bzip2 == null) wtr__bzip2 = Io_stream_wtr_.New_by_mem(bfr, Io_stream_tid_.Tid__bzip2); return wtr__bzip2.Open();
|
||||
case Io_stream_tid_.Tid__xz: if (wtr__xz == null) wtr__xz = Io_stream_wtr_.New_by_mem(bfr, Io_stream_tid_.Tid__xz); return wtr__xz.Open();
|
||||
case Io_stream_tid_.Tid__raw:
|
||||
default: throw Err_.new_unhandled(type);
|
||||
}
|
||||
}
|
||||
private Io_stream_rdr Rdr(byte type) { // TS.MEM: DATE:2016-07-12
|
||||
switch (type) {
|
||||
case Io_stream_.Tid_gzip : return Io_stream_rdr_.new_by_tid_(Io_stream_.Tid_gzip);
|
||||
case Io_stream_.Tid_zip : return Io_stream_rdr_.new_by_tid_(Io_stream_.Tid_zip);
|
||||
case Io_stream_.Tid_bzip2 : return Io_stream_rdr_.new_by_tid_(Io_stream_.Tid_bzip2);
|
||||
case Io_stream_.Tid_raw :
|
||||
default : throw Err_.new_unhandled(type);
|
||||
case Io_stream_tid_.Tid__gzip: return Io_stream_rdr_.New_by_tid(Io_stream_tid_.Tid__gzip);
|
||||
case Io_stream_tid_.Tid__zip: return Io_stream_rdr_.New_by_tid(Io_stream_tid_.Tid__zip);
|
||||
case Io_stream_tid_.Tid__bzip2: return Io_stream_rdr_.New_by_tid(Io_stream_tid_.Tid__bzip2);
|
||||
case Io_stream_tid_.Tid__xz: return Io_stream_rdr_.New_by_tid(Io_stream_tid_.Tid__xz);
|
||||
case Io_stream_tid_.Tid__raw:
|
||||
default: throw Err_.new_unhandled(type);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,22 +18,23 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
package gplx.core.net; import gplx.*; import gplx.core.*;
|
||||
import gplx.core.net.qargs.*;
|
||||
public class Gfo_url {
|
||||
public byte[] Raw() {return raw;} private byte[] raw;
|
||||
public byte Protocol_tid() {return protocol_tid;} private byte protocol_tid;
|
||||
public byte[] Protocol_bry() {return protocol_bry;} private byte[] protocol_bry;
|
||||
public byte[] Anch() {return anch;} private byte[] anch;
|
||||
public Gfo_qarg_itm[] Qargs() {return qargs;} private Gfo_qarg_itm[] qargs;
|
||||
public byte[][] Segs() {return segs;} private byte[][] segs; private int segs__len;
|
||||
public byte[] Segs__get_at(int i) {return i < segs__len ? segs[i] : null;}
|
||||
public byte[] Segs__get_at_1st() {return segs__len > 0 ? segs[0] : null;}
|
||||
public byte[] Segs__get_at_nth() {return segs__len > 1 ? segs[segs__len - 1] : null;}
|
||||
public Gfo_url Ctor(byte[] raw, byte protocol_tid, byte[] protocol_bry, byte[][] segs, Gfo_qarg_itm[] qargs, byte[] anch) {
|
||||
private final int segs__len;
|
||||
public Gfo_url(byte[] raw, byte protocol_tid, byte[] protocol_bry, byte[][] segs, Gfo_qarg_itm[] qargs, byte[] anch) {
|
||||
this.raw = raw;
|
||||
this.protocol_tid = protocol_tid; this.protocol_bry = protocol_bry;
|
||||
this.segs = segs; this.segs__len = segs.length;
|
||||
this.qargs = qargs;
|
||||
this.anch = anch;
|
||||
return this;
|
||||
}
|
||||
public static final Gfo_url Empty = new Gfo_url().Ctor(Bry_.Empty, Gfo_protocol_itm.Tid_unknown, Bry_.Empty, Bry_.Ary_empty, null, null);
|
||||
public byte[] Raw() {return raw;} private final byte[] raw;
|
||||
public byte Protocol_tid() {return protocol_tid;} private final byte protocol_tid;
|
||||
public byte[] Protocol_bry() {return protocol_bry;} private final byte[] protocol_bry;
|
||||
public byte[] Anch() {return anch;} private final byte[] anch;
|
||||
public Gfo_qarg_itm[] Qargs() {return qargs;} private final Gfo_qarg_itm[] qargs;
|
||||
public byte[][] Segs() {return segs;} private final byte[][] segs;
|
||||
public byte[] Segs__get_at(int i) {return i < segs__len ? segs[i] : null;}
|
||||
public byte[] Segs__get_at_1st() {return segs__len > 0 ? segs[0] : null;}
|
||||
public byte[] Segs__get_at_nth() {return segs__len > 1 ? segs[segs__len - 1] : null;}
|
||||
|
||||
public static final Gfo_url Empty = new Gfo_url(Bry_.Empty, Gfo_protocol_itm.Tid_unknown, Bry_.Empty, Bry_.Ary_empty, null, null);
|
||||
}
|
||||
|
||||
@@ -16,20 +16,21 @@ You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.core.net; import gplx.*; import gplx.core.*;
|
||||
import gplx.core.primitives.*; import gplx.core.btries.*;
|
||||
import gplx.core.btries.*;
|
||||
import gplx.core.net.qargs.*;
|
||||
import gplx.langs.htmls.encoders.*;
|
||||
public class Gfo_url_parser {
|
||||
private final Btrie_slim_mgr protocols = Btrie_slim_mgr.ci_a7(); // ASCII:url_protocol; EX:"http:", "ftp:", etc
|
||||
private final Bry_ary segs_ary = new Bry_ary(4), qargs = new Bry_ary(4);
|
||||
private final Bry_bfr tmp_bfr = Bry_bfr_.Reset(500);
|
||||
private final Btrie_rv trv = new Btrie_rv();
|
||||
public byte[] Relative_url_protocol_bry() {return Gfo_protocol_itm.Itm_https.Key_w_colon_bry();} // NOTE: https b/c any WMF wiki will now default to WMF; DATE:2015-07-26
|
||||
private final List_adp segs_list = List_adp_.New(), qargs_list = List_adp_.New();
|
||||
private final Bry_bfr tmp_bfr = Bry_bfr_.Reset(500);
|
||||
public Gfo_url_parser() {
|
||||
Init_protocols(Gfo_protocol_itm.Ary());
|
||||
Init_protocol_itm(Gfo_protocol_itm.Bry_relative, Gfo_protocol_itm.Tid_relative_1);
|
||||
Init_protocol_itm(Gfo_protocol_itm.Bry_file, Gfo_protocol_itm.Tid_file);
|
||||
Init_protocol_itm(gplx.xowa.parsers.lnkes.Xop_lnke_wkr.Bry_xowa_protocol, Gfo_protocol_itm.Tid_xowa);
|
||||
}
|
||||
public byte[] Relative_url_protocol_bry() {return Gfo_protocol_itm.Itm_https.Key_w_colon_bry();} // NOTE: https b/c any WMF wiki will now default to WMF; DATE:2015-07-26
|
||||
private void Init_protocols(Gfo_protocol_itm... itms) {
|
||||
int len = itms.length;
|
||||
for (int i = 0; i < len; i++) {
|
||||
@@ -37,9 +38,7 @@ public class Gfo_url_parser {
|
||||
Init_protocol_itm(itm.Key_w_colon_bry(), itm.Tid());
|
||||
}
|
||||
}
|
||||
public void Init_protocol_itm(byte[] key, byte protocol_tid) {
|
||||
protocols.Add_bry_byte(key, protocol_tid);
|
||||
}
|
||||
public void Init_protocol_itm(byte[] key, byte protocol_tid) {protocols.Add_bry_byte(key, protocol_tid);}
|
||||
public void Parse_site_fast(Gfo_url_site_data site_data, byte[] src, int src_bgn, int src_end) {
|
||||
int pos = src_bgn; boolean rel = false;
|
||||
if (pos + 1 < src_end && src[pos] == Byte_ascii.Slash && src[pos + 1] == Byte_ascii.Slash) { // starts with "//"
|
||||
@@ -62,199 +61,126 @@ public class Gfo_url_parser {
|
||||
slash_pos = Bry_.Trim_end_pos(src, slash_pos);
|
||||
site_data.Atrs_set(rel, pos, slash_pos);
|
||||
}
|
||||
private static final int Area__path = 1, Area__qarg_key_1st = 2, Area__qarg_key_nth = 3, Area__qarg_val = 4, Area__anch = 5;
|
||||
private byte[] src; int src_bgn, src_end;
|
||||
private int area;
|
||||
private boolean encoded;
|
||||
private byte protocol_tid; private byte[] protocol_bry, anch;
|
||||
private int path_bgn, qarg_key_bgn, qarg_val_bgn, anch_bgn, anch_nth_bgn;
|
||||
public Gfo_url Parse(byte[] src) {return Parse(new Gfo_url(), src, 0, src.length);}
|
||||
public Gfo_url Parse(Gfo_url rv, byte[] src, int src_bgn, int src_end) {
|
||||
this.src = src; this.src_bgn = src_bgn; this.src_end = src_end;
|
||||
encoded = false;
|
||||
protocol_tid = Gfo_protocol_itm.Tid_null;
|
||||
protocol_bry = anch = null;
|
||||
path_bgn = qarg_key_bgn = qarg_val_bgn = anch_bgn = anch_nth_bgn = -1;
|
||||
segs_ary.Clear(); qargs.Clear();
|
||||
int pos = src_bgn;
|
||||
Object protocol_obj = protocols.Match_at(trv, src, src_bgn, src_end);
|
||||
pos = trv.Pos();
|
||||
pos = Bry_find_.Find_fwd_while(src, pos, src_end, Byte_ascii.Slash);
|
||||
if (protocol_obj == null) {
|
||||
this.protocol_tid = Gfo_protocol_itm.Tid_unknown;
|
||||
}
|
||||
else {
|
||||
this.protocol_tid = ((Byte_obj_val)protocol_obj).Val();
|
||||
this.protocol_bry = Make_bry(src_bgn, pos);
|
||||
}
|
||||
area = Area__path;
|
||||
path_bgn = pos;
|
||||
while (true) {
|
||||
if (pos == src_end) break;
|
||||
byte b = src[pos];
|
||||
public Gfo_url Parse(byte[] src) {return Parse(src, 0, src.length);}
|
||||
public Gfo_url Parse(byte[] src, int src_bgn, int src_end) {
|
||||
// protocol
|
||||
byte protocol_tid = protocols.Match_byte_or(trv, src, src_bgn, src_end, Gfo_protocol_itm.Tid_unknown);
|
||||
int pos = Bry_find_.Find_fwd_while(src, trv.Pos(), src_end, Byte_ascii.Slash); // set pos after last slash; EX: "https://A" -> position before "A"
|
||||
byte[] protocol_bry = protocol_tid == Gfo_protocol_itm.Tid_unknown
|
||||
? null
|
||||
: Make_bry(false, src, src_bgn, pos);
|
||||
|
||||
// loop chars and handle "/", "#", "?", and "%"
|
||||
boolean encoded = false;
|
||||
int src_zth = src_end - 1;
|
||||
int anch_bgn = -1, qarg_bgn = -1, seg_bgn = pos;
|
||||
for (int i = pos; i < src_end; ++i) {
|
||||
byte b = src[i];
|
||||
switch (b) {
|
||||
case Byte_ascii.Slash: pos = Parse_slash(pos, b); break;
|
||||
case Byte_ascii.Question: pos = Parse_qarg_key_1st(pos, b); break;
|
||||
case Byte_ascii.Amp: pos = Parse_qarg_key_nth(pos, b); break;
|
||||
case Byte_ascii.Eq: pos = Parse_qarg_val(pos, b); break;
|
||||
case Byte_ascii.Hash: if (anch_bgn == -1) pos = Parse_anch(pos, b); else ++pos; break; // anchor begins at 1st #, not last #; EX:A#B#C has anchor of "B#C" not "C" PAGE:en.w:Grand_Central_Terminal; DATE:2015-12-31
|
||||
case Byte_ascii.Percent: encoded = true; ++pos; break;
|
||||
default:
|
||||
++pos;
|
||||
case Byte_ascii.Slash:
|
||||
if (qarg_bgn == -1) { // ignore slash in qargs
|
||||
segs_list.Add(Make_bry(encoded, src, seg_bgn, i));
|
||||
encoded = false;
|
||||
seg_bgn = i + 1; // +1 to skip "/"
|
||||
}
|
||||
break;
|
||||
case Byte_ascii.Hash: // set qarg to first #; also, ignore rest of String; EX: A#B#C -> B#C
|
||||
if (i == src_zth) continue; // ignore # at EOS; EX: "A#"
|
||||
anch_bgn = i;
|
||||
i = src_end;
|
||||
break;
|
||||
case Byte_ascii.Question: // set qarg to last "?"; EX: A?B?C -> C
|
||||
if (i == src_zth) continue; // ignore ? at EOS; EX: "A?"
|
||||
qarg_bgn = i;
|
||||
break;
|
||||
case Byte_ascii.Percent:
|
||||
encoded = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
End_area(pos, Byte_ascii.Null);
|
||||
rv.Ctor(src, protocol_tid, protocol_bry, segs_ary.To_ary(0), Make_qargs(), anch);
|
||||
return rv;
|
||||
}
|
||||
private int Parse_slash(int pos, byte b) {
|
||||
switch (area) {
|
||||
case Area__path: return End_area(pos, b);
|
||||
default: return pos + 1;
|
||||
|
||||
int seg_end = src_end; // set seg_end to src_end; EX: "https://site/A" -> "A"; seg_end may be overriden if "#" or "?" exists
|
||||
|
||||
// set anch
|
||||
byte[] anch = null;
|
||||
if (anch_bgn != -1) {
|
||||
seg_end = anch_bgn; // set seg_end to anch_bgn; EX: "https://site/A#B" -> "A" x> "A#B"
|
||||
anch = Make_bry(encoded, src, anch_bgn + 1, src_end); // +1 to skip "#"
|
||||
}
|
||||
}
|
||||
private int Parse_anch(int pos, byte b) {
|
||||
switch (area) {
|
||||
case Area__path:
|
||||
End_area(pos, b);
|
||||
area = Area__anch;
|
||||
anch_bgn = pos + 1;
|
||||
break;
|
||||
case Area__anch: // handle double; A#B#C -> "A#B", "C"
|
||||
Append_to_last_path(Byte_ascii.Hash, Make_bry(anch_bgn, pos));
|
||||
anch_bgn = pos + 1;
|
||||
break;
|
||||
case Area__qarg_val:
|
||||
case Area__qarg_key_1st:
|
||||
case Area__qarg_key_nth:
|
||||
if (anch_nth_bgn == -1)
|
||||
anch_nth_bgn = Bry_find_.Find_bwd(src, Byte_ascii.Hash, src_end);
|
||||
if (pos == anch_nth_bgn) {
|
||||
End_area(pos, b);
|
||||
area = Area__anch;
|
||||
anch_bgn = pos + 1;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
|
||||
// set qargs
|
||||
Gfo_qarg_itm[] qarg_ary = Gfo_qarg_itm.Ary_empty;
|
||||
if (qarg_bgn != -1) {
|
||||
int qarg_end = anch_bgn == -1
|
||||
? src_end // # missing; set to src_end; EX: "A?B=C" -> EOS
|
||||
: anch_bgn; // # exists; set to anch_bgn; EX: "A?B=C#D" -> #
|
||||
qarg_ary = Make_qarg_ary(src, qarg_bgn, qarg_end);
|
||||
seg_end = qarg_ary.length == 0
|
||||
? src_end // set seg_end to src_end if pseudo qarg; EX: "https://site/A?B" -> "A?B" x> "A"
|
||||
: qarg_bgn; // set seg_end to qarg_bgn; EX: "https://site/A?B=C" -> "A" x> "A#B"; NOTE: overrides anch; "A?B=C#D" -> "A"
|
||||
}
|
||||
return pos + 1;
|
||||
|
||||
// extract seg_end; note that there will always be a seg_end; if src ends with slash, then it will be ""; EX: "A/" -> "A", ""
|
||||
segs_list.Add(Make_bry(encoded, src, seg_bgn, seg_end));
|
||||
|
||||
// build url and return it
|
||||
return new Gfo_url(src, protocol_tid, protocol_bry, (byte[][])segs_list.To_ary_and_clear(byte[].class), qarg_ary, anch);
|
||||
}
|
||||
private int Parse_qarg_key_1st(int pos, byte b) {
|
||||
switch (area) {
|
||||
case Area__path: // only valid way to start qarg; EX: A?B=C
|
||||
End_area(pos, b);
|
||||
area = Area__qarg_key_1st;
|
||||
qarg_key_bgn = pos + 1;
|
||||
break;
|
||||
case Area__qarg_key_1st: // handle dupe; EX: A?B?C
|
||||
case Area__qarg_key_nth: // handle dupe; EX: A?B=C&D?
|
||||
case Area__qarg_val: // handle dupe; EX: A?B=?
|
||||
End_area(pos, b);
|
||||
Append_to_last_path__qargs();
|
||||
area = Area__qarg_key_1st;
|
||||
qarg_key_bgn = pos + 1;
|
||||
break;
|
||||
private Gfo_qarg_itm[] Make_qarg_ary(byte[] src, int qarg_bgn, int qarg_end) {
|
||||
// init
|
||||
int key_bgn = qarg_bgn + 1; // +1 to skip "?"
|
||||
byte[] key_bry = null;
|
||||
int val_bgn = -1;
|
||||
boolean encoded = false;
|
||||
|
||||
// loop qarg for "&", "=", "%"
|
||||
int qarg_pos = qarg_bgn;
|
||||
while (true) {
|
||||
boolean b_is_last = qarg_pos == qarg_end;
|
||||
byte b = b_is_last ? Byte_ascii.Null : src[qarg_pos];
|
||||
boolean make_qarg = false;
|
||||
switch (b) {
|
||||
case Byte_ascii.Amp: // "&" always makes qarg
|
||||
make_qarg = true;
|
||||
break;
|
||||
case Byte_ascii.Null: // "EOS" makes qarg as long as "=" seen or at least one qarg; specifically, "A?B" shouldn't make qarg
|
||||
if ( val_bgn != -1 // "=" seen; EX: "?A=B"
|
||||
|| qargs_list.Count() > 0) // at least one qarg exists; EX: "?A=B&C"
|
||||
make_qarg = true;
|
||||
break;
|
||||
case Byte_ascii.Eq:
|
||||
key_bry = Make_bry(encoded, src, key_bgn, qarg_pos);
|
||||
encoded = false;
|
||||
val_bgn = qarg_pos + 1;
|
||||
break;
|
||||
case Byte_ascii.Percent:
|
||||
encoded = true;
|
||||
break;
|
||||
}
|
||||
|
||||
// make qarg
|
||||
if (make_qarg) {
|
||||
byte[] val_bry = null;
|
||||
if (key_bry == null) // key missing; EX: "&A" -> "A,null"
|
||||
key_bry = Make_bry(encoded, src, key_bgn, qarg_pos);
|
||||
else // key exists; EX: "&A=B" -> "A,B"
|
||||
val_bry = Make_bry(encoded, src, val_bgn, qarg_pos);
|
||||
encoded = false;
|
||||
qargs_list.Add(new Gfo_qarg_itm(key_bry, val_bry));
|
||||
|
||||
// reset vars
|
||||
key_bry = null;
|
||||
key_bgn = qarg_pos + 1;
|
||||
val_bgn = -1;
|
||||
}
|
||||
if (b_is_last) break;
|
||||
++qarg_pos;
|
||||
}
|
||||
return pos + 1;
|
||||
}
|
||||
private int Parse_qarg_key_nth(int pos, byte b) {
|
||||
switch (area) {
|
||||
case Area__path: // ignore if qarg not started; EX: A&B
|
||||
break;
|
||||
case Area__qarg_key_1st: // handle invalid; A?B&C
|
||||
case Area__qarg_key_nth: // handle invalid; A?B=C&D&E=F
|
||||
End_area(pos, b);
|
||||
qargs.Add(null);
|
||||
area = Area__qarg_key_nth;
|
||||
qarg_key_bgn = pos + 1;
|
||||
break;
|
||||
case Area__qarg_val:
|
||||
End_area(pos, b);
|
||||
area = Area__qarg_key_nth;
|
||||
qarg_key_bgn = pos + 1;
|
||||
break;
|
||||
}
|
||||
return pos + 1;
|
||||
}
|
||||
private int Parse_qarg_val(int pos, byte b) {
|
||||
switch (area) {
|
||||
case Area__qarg_key_1st:
|
||||
case Area__qarg_key_nth:
|
||||
End_area(pos, b); break;
|
||||
default: break;
|
||||
}
|
||||
return pos + 1;
|
||||
}
|
||||
private int End_area(int pos, byte b) {
|
||||
switch (area) {
|
||||
case Area__path:
|
||||
segs_ary.Add(Make_bry(path_bgn, pos));
|
||||
path_bgn = pos + 1;
|
||||
break;
|
||||
case Area__qarg_key_1st:
|
||||
case Area__qarg_key_nth:
|
||||
if (b == Byte_ascii.Null && qargs.Len() == 0) // handle A?b but not A?b=c&d
|
||||
Append_to_last_path(Byte_ascii.Question, Make_bry(qarg_key_bgn, src_end));
|
||||
else {
|
||||
qargs.Add(Make_bry(qarg_key_bgn, pos));
|
||||
qarg_val_bgn = pos + 1;
|
||||
area = Area__qarg_val;
|
||||
}
|
||||
break;
|
||||
case Area__qarg_val:
|
||||
qargs.Add(Make_bry(qarg_val_bgn, pos));
|
||||
qarg_key_bgn = pos + 1;
|
||||
qarg_val_bgn = -1;
|
||||
area = Area__qarg_key_nth;
|
||||
break;
|
||||
case Area__anch:
|
||||
if (b == Byte_ascii.Null && anch_bgn == src_end) // handle A# but not "A#B"
|
||||
Append_to_last_path(Byte_ascii.Hash, Make_bry(anch_bgn, src_end));
|
||||
else
|
||||
anch = Make_bry(anch_bgn, pos);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
encoded = false;
|
||||
return pos + 1;
|
||||
}
|
||||
private byte[] Make_bry(int bgn, int end) {
|
||||
return encoded ? gplx.langs.htmls.encoders.Gfo_url_encoder_.Xourl.Decode(tmp_bfr, Bool_.N, src, bgn, end).To_bry_and_clear() : Bry_.Mid(src, bgn, end);
|
||||
}
|
||||
private Gfo_qarg_itm[] Make_qargs() {
|
||||
int qargs_len = qargs.Len(); if (qargs_len == 0) return Gfo_qarg_itm.Ary_empty;
|
||||
if (qargs_len % 2 == 1) ++qargs_len; // handle odd qargs; EX: ?A=B&C&D=E
|
||||
Gfo_qarg_itm[] rv = new Gfo_qarg_itm[qargs_len / 2];
|
||||
for (int i = 0; i < qargs_len; i += 2) {
|
||||
byte[] key = qargs.Get_at(i);
|
||||
int val_idx = i + 1;
|
||||
byte[] val = val_idx < qargs_len ? qargs.Get_at(val_idx) : null;
|
||||
rv[i / 2] = new Gfo_qarg_itm(key, val);
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
private void Append_to_last_path(byte b, byte[] append) {
|
||||
byte[] last_path = segs_ary.Get_at_last(); if (last_path == null) return;
|
||||
last_path = Bry_.Add_w_dlm(b, last_path, append);
|
||||
segs_ary.Set_at_last(last_path);
|
||||
}
|
||||
private void Append_to_last_path__qargs() {
|
||||
byte[] last_path = segs_ary.Get_at_last(); if (last_path == null) return;
|
||||
tmp_bfr.Add(last_path);
|
||||
int len = qargs.Len();
|
||||
if (len % 2 == 1) qargs.Add(null); // handle odd qargs
|
||||
for (int i = 0; i < len; i += 2) {
|
||||
tmp_bfr.Add_byte(i == 0 ? Byte_ascii.Question : Byte_ascii.Amp);
|
||||
tmp_bfr.Add(qargs.Get_at(i));
|
||||
byte[] qarg_val = qargs.Get_at(i + 1);
|
||||
if (qarg_val != null) // handle "null" added above
|
||||
tmp_bfr.Add_byte_eq().Add(qarg_val);
|
||||
}
|
||||
qargs.Clear();
|
||||
segs_ary.Set_at_last(tmp_bfr.To_bry_and_clear());
|
||||
return (Gfo_qarg_itm[])qargs_list.To_ary_and_clear(Gfo_qarg_itm.class);
|
||||
}
|
||||
private byte[] Make_bry(boolean encoded, byte[] src, int bgn, int end) {
|
||||
return encoded ? Gfo_url_encoder_.Xourl.Decode(tmp_bfr, Bool_.N, src, bgn, end).To_bry_and_clear() : Bry_.Mid(src, bgn, end);
|
||||
}
|
||||
|
||||
public static final byte[] Bry_double_slash = new byte[] {Byte_ascii.Slash, Byte_ascii.Slash};
|
||||
}
|
||||
|
||||
@@ -20,15 +20,19 @@ import gplx.core.net.qargs.*;
|
||||
class Gfo_url_parser_fxt {
|
||||
private final Gfo_url_parser parser = new Gfo_url_parser();
|
||||
private Gfo_url actl;
|
||||
public Gfo_url_parser_fxt Chk_protocol_tid(byte v) {Tfds.Eq_byte(v, actl.Protocol_tid(), "protocol_tid"); return this;}
|
||||
public Gfo_url_parser_fxt Chk_protocol_bry(String v) {Tfds.Eq_str(v, actl.Protocol_bry(), "protocol_bry"); return this;}
|
||||
public Gfo_url_parser_fxt Chk_site(String v) {Tfds.Eq_str(v, actl.Segs__get_at_1st(), "site"); return this;}
|
||||
public Gfo_url_parser_fxt Chk_page(String v) {Tfds.Eq_str(v, actl.Segs__get_at_nth(), "page"); return this;}
|
||||
public Gfo_url_parser_fxt Chk_anch(String v) {Tfds.Eq_str(v, actl.Anch(), "anch"); return this;}
|
||||
public Gfo_url_parser_fxt Chk_segs(String... ary) {Tfds.Eq_int(ary.length, actl.Segs().length, "segs_len"); Tfds.Eq_str_lines(String_.Concat_lines_nl(ary), String_.Concat_lines_nl(String_.Ary(actl.Segs())), "segs"); return this;}
|
||||
public Gfo_url_parser_fxt Chk_qargs(String... ary) {Tfds.Eq_str_lines(String_.To_str__as_kv_ary(ary), Gfo_qarg_itm.To_str(actl.Qargs()), "qargs"); return this;}
|
||||
public Gfo_url_parser_fxt Run_parse(String v) {
|
||||
this.actl = parser.Parse(Bry_.new_u8(v));
|
||||
public Gfo_url_parser_fxt Test__protocol_tid(byte v) {Tfds.Eq_byte(v, actl.Protocol_tid(), "protocol_tid"); return this;}
|
||||
public Gfo_url_parser_fxt Test__protocol_bry(String v) {Tfds.Eq_str(v, actl.Protocol_bry(), "protocol_bry"); return this;}
|
||||
public Gfo_url_parser_fxt Test__site(String v) {Tfds.Eq_str(v, actl.Segs__get_at_1st(), "site"); return this;}
|
||||
public Gfo_url_parser_fxt Test__page(String v) {Tfds.Eq_str(v, actl.Segs__get_at_nth(), "page"); return this;}
|
||||
public Gfo_url_parser_fxt Test__anch(String v) {Tfds.Eq_str(v, actl.Anch(), "anch"); return this;}
|
||||
public Gfo_url_parser_fxt Test__segs(String... ary) {
|
||||
Tfds.Eq_str_lines(String_.Concat_lines_nl(ary), String_.Concat_lines_nl(String_.Ary(actl.Segs())), "segs");
|
||||
Tfds.Eq_int(ary.length, actl.Segs().length, "segs_len");
|
||||
return this;
|
||||
}
|
||||
public Gfo_url_parser_fxt Test__qargs(String... ary) {Tfds.Eq_str_lines(String_.To_str__as_kv_ary(ary), Qargs__To_str(actl.Qargs()), "qargs"); return this;}
|
||||
public Gfo_url_parser_fxt Exec__parse(String v) {
|
||||
this.actl = parser.Parse(Bry_.new_u8(v), 0, String_.Len(v));
|
||||
return this;
|
||||
}
|
||||
public void Test_Parse_site_fast(String raw, String expd) {
|
||||
@@ -37,4 +41,16 @@ class Gfo_url_parser_fxt {
|
||||
String actl = String_.new_u8(raw_bry, site_data.Site_bgn(), site_data.Site_end());
|
||||
Tfds.Eq(expd, actl);
|
||||
} private final Gfo_url_site_data site_data = new Gfo_url_site_data();
|
||||
private static String Qargs__To_str(Gfo_qarg_itm[] ary) {
|
||||
int len = ary.length;
|
||||
Bry_bfr bfr = Bry_bfr_.New();
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Gfo_qarg_itm itm = ary[i];
|
||||
bfr.Add(itm.Key_bry()).Add_byte_eq();
|
||||
if (itm.Val_bry() != null)
|
||||
bfr.Add(itm.Val_bry());
|
||||
bfr.Add_byte_nl();
|
||||
}
|
||||
return bfr.To_str_and_clear();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,102 +18,102 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
package gplx.core.net; import gplx.*; import gplx.core.*;
|
||||
import org.junit.*;
|
||||
public class Gfo_url_parser_tst {
|
||||
private final Gfo_url_parser_fxt tstr = new Gfo_url_parser_fxt();
|
||||
private final Gfo_url_parser_fxt tstr = new Gfo_url_parser_fxt();
|
||||
@Test public void Protocol__relative() {
|
||||
tstr.Run_parse("//en.wikipedia.org").Chk_protocol_tid(Gfo_protocol_itm.Tid_relative_1).Chk_protocol_bry("//").Chk_site("en.wikipedia.org");
|
||||
tstr.Exec__parse("//en.wikipedia.org").Test__protocol_tid(Gfo_protocol_itm.Tid_relative_1).Test__protocol_bry("//").Test__site("en.wikipedia.org");
|
||||
}
|
||||
@Test public void Protocol__none() {
|
||||
tstr.Run_parse("en.wikipedia.org/wiki/A").Chk_protocol_tid(Gfo_protocol_itm.Tid_unknown).Chk_segs("en.wikipedia.org", "wiki", "A");
|
||||
tstr.Exec__parse("en.wikipedia.org/wiki/A").Test__protocol_tid(Gfo_protocol_itm.Tid_unknown).Test__segs("en.wikipedia.org", "wiki", "A");
|
||||
}
|
||||
@Test public void Site__parts__3() {
|
||||
tstr.Run_parse("https://en.wikipedia.org").Chk_protocol_tid(Gfo_protocol_itm.Tid_https).Chk_protocol_bry("https://").Chk_segs("en.wikipedia.org");
|
||||
tstr.Exec__parse("https://en.wikipedia.org").Test__protocol_tid(Gfo_protocol_itm.Tid_https).Test__protocol_bry("https://").Test__segs("en.wikipedia.org");
|
||||
}
|
||||
@Test public void Site__parts__2() {
|
||||
tstr.Run_parse("https://wikipedia.org").Chk_protocol_tid(Gfo_protocol_itm.Tid_https).Chk_segs("wikipedia.org");
|
||||
tstr.Exec__parse("https://wikipedia.org").Test__protocol_tid(Gfo_protocol_itm.Tid_https).Test__segs("wikipedia.org");
|
||||
}
|
||||
@Test public void Site__parts__1() {
|
||||
tstr.Run_parse("https://wikipedia").Chk_protocol_tid(Gfo_protocol_itm.Tid_https).Chk_segs("wikipedia");
|
||||
tstr.Exec__parse("https://wikipedia").Test__protocol_tid(Gfo_protocol_itm.Tid_https).Test__segs("wikipedia");
|
||||
}
|
||||
@Test public void Site__slash__none() {
|
||||
tstr.Run_parse("https:site").Chk_protocol_tid(Gfo_protocol_itm.Tid_https).Chk_site("site");
|
||||
tstr.Exec__parse("https:site").Test__protocol_tid(Gfo_protocol_itm.Tid_https).Test__site("site");
|
||||
}
|
||||
@Test public void Site__slash__eos() {
|
||||
tstr.Exec__parse("https://en.wikipedia.org/").Test__protocol_tid(Gfo_protocol_itm.Tid_https).Test__site("en.wikipedia.org");
|
||||
}
|
||||
@Test public void Paths__1() {
|
||||
tstr.Run_parse("https://site/A").Chk_segs("site", "A");
|
||||
tstr.Exec__parse("https://site/A").Test__segs("site", "A");
|
||||
}
|
||||
@Test public void Paths__2() {
|
||||
tstr.Run_parse("https://site/wiki/A").Chk_segs("site", "wiki", "A");
|
||||
tstr.Exec__parse("https://site/wiki/A").Test__segs("site", "wiki", "A");
|
||||
}
|
||||
@Test public void Paths__n() {
|
||||
tstr.Run_parse("https://site/wiki/A/B/C/D").Chk_segs("site", "wiki", "A", "B", "C", "D");
|
||||
tstr.Exec__parse("https://site/wiki/A/B/C/D").Test__segs("site", "wiki", "A", "B", "C", "D");
|
||||
}
|
||||
@Test public void Qargs__1() {
|
||||
tstr.Run_parse("https://site/A?B=C").Chk_page("A").Chk_qargs("B", "C");
|
||||
tstr.Exec__parse("https://site/A?B=C").Test__page("A").Test__qargs("B", "C");
|
||||
}
|
||||
@Test public void Qargs__2() {
|
||||
tstr.Run_parse("https://site/A?B=C&D=E").Chk_page("A").Chk_qargs("B", "C", "D", "E");
|
||||
tstr.Exec__parse("https://site/A?B=C&D=E").Test__page("A").Test__qargs("B", "C", "D", "E");
|
||||
}
|
||||
@Test public void Qargs__3() {
|
||||
tstr.Run_parse("https://site/A?B=C&D=E&F=G").Chk_page("A").Chk_qargs("B", "C", "D", "E", "F", "G");
|
||||
tstr.Exec__parse("https://site/A?B=C&D=E&F=G").Test__page("A").Test__qargs("B", "C", "D", "E", "F", "G");
|
||||
}
|
||||
@Test public void Qargs__ques__dupe__ques() {
|
||||
tstr.Run_parse("https://site/A?B?Y=Z").Chk_page("A?B").Chk_qargs("Y", "Z");
|
||||
tstr.Exec__parse("https://site/A?B?Y=Z").Test__page("A?B").Test__qargs("Y", "Z");
|
||||
}
|
||||
@Test public void Qargs__ques__dupe__amp() {
|
||||
tstr.Run_parse("https://site/A?B=C&D?Y=Z").Chk_page("A?B=C&D").Chk_qargs("Y", "Z");
|
||||
tstr.Exec__parse("https://site/A?B=C&D?Y=Z").Test__page("A?B=C&D").Test__qargs("Y", "Z");
|
||||
}
|
||||
@Test public void Qargs__ques__dupe__eq() {
|
||||
tstr.Run_parse("https://site/A?B=C?Y=Z").Chk_page("A?B=C").Chk_qargs("Y", "Z");
|
||||
tstr.Exec__parse("https://site/A?B=C?Y=Z").Test__page("A?B=C").Test__qargs("Y", "Z");
|
||||
}
|
||||
@Test public void Qargs__amp__dupe__ques() {
|
||||
tstr.Run_parse("https://site/A?B&Y=Z").Chk_page("A").Chk_qargs("B", null, "Y", "Z");
|
||||
tstr.Exec__parse("https://site/A?B&Y=Z").Test__page("A").Test__qargs("B", null, "Y", "Z");
|
||||
}
|
||||
@Test public void Qargs__amp__dupe__amp() {
|
||||
tstr.Run_parse("https://site/A?B=C&D&Y=Z").Chk_page("A").Chk_qargs("B", "C", "D", null, "Y", "Z");
|
||||
tstr.Exec__parse("https://site/A?B=C&D&Y=Z").Test__page("A").Test__qargs("B", "C", "D", null, "Y", "Z");
|
||||
}
|
||||
@Test public void Qargs__missing_val__0() {
|
||||
tstr.Run_parse("https://site/A?").Chk_page("A?").Chk_qargs();
|
||||
tstr.Exec__parse("https://site/A?").Test__page("A?").Test__qargs();
|
||||
}
|
||||
@Test public void Qargs__missing_val__2() {
|
||||
tstr.Run_parse("https://site/A?B=C&D&F=G").Chk_page("A").Chk_qargs("B", "C", "D", null, "F", "G");
|
||||
tstr.Exec__parse("https://site/A?B=C&D&F=G").Test__page("A").Test__qargs("B", "C", "D", null, "F", "G");
|
||||
}
|
||||
@Test public void Qargs__missing_val__n() {
|
||||
tstr.Run_parse("https://site/A?B=C&D=E&F").Chk_page("A").Chk_qargs("B", "C", "D", "E", "F", null);
|
||||
tstr.Exec__parse("https://site/A?B=C&D=E&F").Test__page("A").Test__qargs("B", "C", "D", "E", "F", null);
|
||||
}
|
||||
@Test public void Qargs__site_less__missing__0() {
|
||||
tstr.Run_parse("A?B").Chk_segs("A?B").Chk_qargs();
|
||||
tstr.Exec__parse("A?B").Test__segs("A?B").Test__qargs();
|
||||
}
|
||||
@Test public void Qargs__site_less() {
|
||||
tstr.Run_parse("A?B=C&D=E").Chk_site("A").Chk_qargs("B", "C", "D", "E");
|
||||
tstr.Exec__parse("A?B=C&D=E").Test__site("A").Test__qargs("B", "C", "D", "E");
|
||||
}
|
||||
@Test public void Anch__basic() {
|
||||
tstr.Run_parse("https://site/A#B").Chk_page("A").Chk_anch("B");
|
||||
tstr.Exec__parse("https://site/A#B").Test__page("A").Test__anch("B");
|
||||
}
|
||||
@Test public void Anch__repeat__2() {
|
||||
tstr.Run_parse("https://site/A#B#C").Chk_page("A").Chk_anch("B#C");
|
||||
tstr.Exec__parse("https://site/A#B#C").Test__page("A").Test__anch("B#C");
|
||||
}
|
||||
@Test public void Anch__repeat__3() {
|
||||
tstr.Run_parse("https://site/A#B#C#D").Chk_page("A").Chk_anch("B#C#D");
|
||||
tstr.Exec__parse("https://site/A#B#C#D").Test__page("A").Test__anch("B#C#D");
|
||||
}
|
||||
@Test public void Anch__missing() {
|
||||
tstr.Run_parse("https://site/A#").Chk_page("A#").Chk_anch(null);
|
||||
tstr.Exec__parse("https://site/A#").Test__page("A#").Test__anch(null);
|
||||
}
|
||||
@Test public void Anch__missing__eos() {
|
||||
tstr.Run_parse("https://site/A#B#").Chk_page("A").Chk_anch("B#");
|
||||
tstr.Exec__parse("https://site/A#B#").Test__page("A").Test__anch("B#");
|
||||
}
|
||||
@Test public void Anch__qargs__basic() {
|
||||
tstr.Run_parse("https://site/A?B=C&D=E#F").Chk_page("A").Chk_qargs("B", "C", "D", "E").Chk_anch("F");
|
||||
}
|
||||
@Test public void Anch__qargs__repeat() {
|
||||
tstr.Run_parse("https://site/A?B=C#&D=E#F").Chk_page("A").Chk_qargs("B", "C#", "D", "E").Chk_anch("F");
|
||||
tstr.Exec__parse("https://site/A?B=C&D=E#F").Test__page("A").Test__qargs("B", "C", "D", "E").Test__anch("F");
|
||||
}
|
||||
@Test public void Anch__site_less() {
|
||||
tstr.Run_parse("A#B").Chk_site("A").Chk_anch("B");
|
||||
tstr.Exec__parse("A#B").Test__site("A").Test__anch("B");
|
||||
}
|
||||
@Test public void Encode__page() {
|
||||
tstr.Run_parse("http://site/A%27s").Chk_site("site").Chk_page("A's");
|
||||
tstr.Exec__parse("http://site/A%27s").Test__site("site").Test__page("A's");
|
||||
}
|
||||
@Test public void Protocol_less__qargs() {
|
||||
tstr.Run_parse("Special:Search/Earth?fulltext=yes").Chk_segs("Special:Search", "Earth").Chk_page("Earth").Chk_qargs("fulltext", "yes");
|
||||
tstr.Exec__parse("Special:Search/Earth?fulltext=yes").Test__segs("Special:Search", "Earth").Test__page("Earth").Test__qargs("fulltext", "yes");
|
||||
}
|
||||
@Test public void Parse_site_fast() {
|
||||
tstr.Test_Parse_site_fast("http://a.org/B" , "a.org");
|
||||
@@ -121,4 +121,8 @@ public class Gfo_url_parser_tst {
|
||||
tstr.Test_Parse_site_fast("//a.org/B" , "a.org");
|
||||
tstr.Test_Parse_site_fast("//a.org/B:C" , "a.org");
|
||||
}
|
||||
// DELETED: logic isn't right; anch is first # not last; EX: https://en.wikipedia.org/w/index.php?title=Category:2001_albums&pagefrom=Beautiful+#View#mw-pages; DATE:2016-10-10
|
||||
// @Test public void Anch__qargs__repeat() {
|
||||
// tstr.Exec__parse("https://site/A?B=C#&D=E#F").Test__page("A").Test__qargs("B", "C#", "D", "E").Test__anch("F");
|
||||
// }
|
||||
}
|
||||
|
||||
@@ -17,35 +17,13 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.core.net.qargs; import gplx.*; import gplx.core.*; import gplx.core.net.*;
|
||||
public class Gfo_qarg_itm {
|
||||
public Gfo_qarg_itm(byte[] key_bry, byte[] val_bry) {this.key_bry = key_bry; this.val_bry = val_bry;}
|
||||
public byte[] Key_bry() {return key_bry;} private byte[] key_bry;
|
||||
public byte[] Val_bry() {return val_bry;} private byte[] val_bry;
|
||||
public Gfo_qarg_itm Val_bry_(byte[] v) {val_bry = v; return this;}
|
||||
public Gfo_qarg_itm(byte[] key_bry, byte[] val_bry) {
|
||||
this.key_bry = key_bry;
|
||||
this.val_bry = val_bry;
|
||||
}
|
||||
public byte[] Key_bry() {return key_bry;} private final byte[] key_bry;
|
||||
public byte[] Val_bry() {return val_bry;} private byte[] val_bry;
|
||||
public void Val_bry_(byte[] v) {val_bry = v;}
|
||||
|
||||
public static final Gfo_qarg_itm[] Ary_empty = new Gfo_qarg_itm[0];
|
||||
public static Gfo_qarg_itm new_key_(String key) {return new Gfo_qarg_itm(Bry_.new_u8(key), Bry_.Empty);}
|
||||
public static Gfo_qarg_itm[] Ary(String... kvs) {
|
||||
int len = kvs.length;
|
||||
Gfo_qarg_itm[] rv = new Gfo_qarg_itm[len / 2];
|
||||
String key = null;
|
||||
for (int i = 0; i < len; ++i) {
|
||||
String s = kvs[i];
|
||||
if (i % 2 == 0)
|
||||
key = s;
|
||||
else
|
||||
rv[i / 2] = new Gfo_qarg_itm(Bry_.new_u8(key), Bry_.new_u8(s));
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
public static String To_str(Gfo_qarg_itm[] ary) {
|
||||
int len = ary.length;
|
||||
Bry_bfr bfr = Bry_bfr_.New();
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Gfo_qarg_itm itm = ary[i];
|
||||
bfr.Add(itm.Key_bry()).Add_byte_eq();
|
||||
if (itm.Val_bry() != null)
|
||||
bfr.Add(itm.Val_bry());
|
||||
bfr.Add_byte_nl();
|
||||
}
|
||||
return bfr.To_str_and_clear();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -48,8 +48,7 @@ public class Fsd_bin_tbl implements Rls_able {
|
||||
stmt_insert = conn.Stmt_insert(tbl_name, flds);
|
||||
tmp_bfr = Bry_bfr_.Reset(Io_mgr.Len_kb);
|
||||
}
|
||||
byte[] bin_ary = null;
|
||||
bin_ary = Io_stream_rdr_.Load_all_as_bry(tmp_bfr, bin_rdr);
|
||||
byte[] bin_ary = Io_stream_rdr_.Load_all_as_bry(tmp_bfr, bin_rdr);
|
||||
stmt_insert.Clear()
|
||||
.Val_int(fld_owner_id, id)
|
||||
.Val_byte(fld_owner_tid, tid)
|
||||
@@ -62,7 +61,7 @@ public class Fsd_bin_tbl implements Rls_able {
|
||||
byte[] rv = Select(owner_id, null);
|
||||
return rv == null
|
||||
? Io_stream_rdr_.Noop
|
||||
: Io_stream_rdr_.mem_(rv);
|
||||
: Io_stream_rdr_.New__mem(rv);
|
||||
}
|
||||
public boolean Select_to_url(int owner_id, Io_url url) {
|
||||
saved_in_parts.Val_n();
|
||||
|
||||
@@ -32,7 +32,7 @@ public class Xoa_app_ {
|
||||
}
|
||||
}
|
||||
public static final String Name = "xowa";
|
||||
public static final String Version = "3.9.4.1";
|
||||
public static final String Version = "3.9.4.4";
|
||||
public static String Build_date = "2012-12-30 00:00:00";
|
||||
public static String Op_sys_str;
|
||||
public static String User_agent = "";
|
||||
|
||||
@@ -36,7 +36,7 @@ public class Xoa_app_fxt {
|
||||
Io_url user_dir = root_dir.GenSubDir_nest("user", "test_user");
|
||||
Gfo_usr_dlg__log_base.Instance.Log_dir_(user_dir.GenSubDir_nest("tmp", "current"));
|
||||
Xoae_app app = new Xoae_app(Gfo_usr_dlg_.Test(), Xoa_app_mode.Itm_cmd, root_dir, root_dir.GenSubDir("wiki"), root_dir.GenSubDir("file"), user_dir, root_dir.GenSubDir_nest("user", "anonymous", "wiki"), op_sys);
|
||||
app.Setup_mgr().Dump_mgr().Data_storage_format_(gplx.core.ios.streams.Io_stream_.Tid_raw); // TEST: set data_storage_format to file, else bldr tests will fails (expects plain text)
|
||||
app.Setup_mgr().Dump_mgr().Data_storage_format_(gplx.core.ios.streams.Io_stream_tid_.Tid__raw); // TEST: set data_storage_format to file, else bldr tests will fails (expects plain text)
|
||||
GfsCore.Instance.Clear(); // NOTE: must clear
|
||||
GfsCore.Instance.AddCmd(app, Xoae_app.Invk_app); // NOTE: must add app to GfsCore; app.Gfs_mgr() always adds current app to GfsCore; note this causes old test to leave behind GfsCore for new test
|
||||
GfsCore.Instance.AddCmd(app, Xoae_app.Invk_xowa); // add alias for app; DATE:2014-06-09
|
||||
|
||||
@@ -21,6 +21,7 @@ import gplx.xowa.htmls.hrefs.*;
|
||||
public class Xoa_url {
|
||||
public int Tid() {return tid;} private int tid;
|
||||
public byte[] Raw() {return raw;} private byte[] raw = Bry_.Empty;
|
||||
public byte[] Orig() {return orig;} private byte[] orig;
|
||||
public byte[] Wiki_bry() {return wiki_bry;} public Xoa_url Wiki_bry_(byte[] v) {wiki_bry = v; return this;} private byte[] wiki_bry;
|
||||
public byte[] Page_bry() {return page_bry;} public Xoa_url Page_bry_(byte[] v) {page_bry = v; return this;} private byte[] page_bry;
|
||||
public byte[] Anch_bry() {return anch_bry;} public Xoa_url Anch_bry_(byte[] v) {anch_bry = v; return this;} private byte[] anch_bry;
|
||||
@@ -35,10 +36,10 @@ public class Xoa_url {
|
||||
public boolean Wiki_is_missing() {return wiki_is_missing;} private boolean wiki_is_missing;
|
||||
public boolean Wiki_is_same() {return wiki_is_same;} private boolean wiki_is_same;
|
||||
public boolean Page_is_main() {return page_is_main;} private boolean page_is_main;
|
||||
public Xoa_url Ctor(int tid, byte[] raw, byte protocol_tid, byte[] protocol_bry, boolean protocol_is_relative
|
||||
public Xoa_url Ctor(int tid, byte[] orig, byte[] raw, byte protocol_tid, byte[] protocol_bry, boolean protocol_is_relative
|
||||
, byte[] wiki, byte[] page, Gfo_qarg_itm[] qargs, byte[] anch
|
||||
, byte[][] segs_ary, byte[] vnt_bry, boolean wiki_is_missing, boolean wiki_is_same, boolean page_is_main) {
|
||||
this.tid = tid; this.raw = raw;
|
||||
this.tid = tid; this.orig = orig; this.raw = raw;
|
||||
this.protocol_tid = protocol_tid; this.protocol_bry = protocol_bry; this.protocol_is_relative = protocol_is_relative;
|
||||
this.wiki_bry = wiki; this.page_bry = page; this.qargs_ary = qargs; this.anch_bry = anch;
|
||||
this.segs_ary = segs_ary; this.vnt_bry = vnt_bry;
|
||||
@@ -92,21 +93,16 @@ public class Xoa_url {
|
||||
if (tid_is_anch)
|
||||
page = null;
|
||||
}
|
||||
byte[] rv = Bry_.Add
|
||||
( wiki, wiki_spr // add wiki_key; EX: "en.wikipedia.org", "/wiki/"
|
||||
, page // add page; EX: "A"
|
||||
, anch_spr, anch // add anch EX: "#", "B"
|
||||
);
|
||||
|
||||
Bry_bfr bfr = Bry_bfr_.New();
|
||||
bfr.Add_safe(wiki).Add_safe(wiki_spr); // add wiki_key; EX: "en.wikipedia.org", "/wiki/"
|
||||
bfr.Add_safe(page); // add page; EX: "A"
|
||||
if (show_qargs || qargs_ary.length > 0) {
|
||||
Bry_bfr bfr = Bry_bfr_.New();
|
||||
try {
|
||||
bfr.Add(rv);
|
||||
Gfo_qarg_mgr_old.Concat_bfr(bfr, gplx.langs.htmls.encoders.Gfo_url_encoder_.Href, qargs_ary);
|
||||
return bfr.To_bry_and_clear();
|
||||
} finally {bfr.Mkr_rls();}
|
||||
Gfo_qarg_mgr_old.Concat_bfr(bfr, gplx.langs.htmls.encoders.Gfo_url_encoder_.Href, qargs_ary);
|
||||
}
|
||||
else
|
||||
return rv;
|
||||
if (anch != null) // NOTE: anch must go last (after qargs); DATE:2016-10-08
|
||||
bfr.Add(anch_spr).Add(anch); // add anch EX: "#", "B"
|
||||
return bfr.To_bry_and_clear();
|
||||
}
|
||||
public static final Xoa_url Null = null;
|
||||
public static Xoa_url blank() {return new Xoa_url();}
|
||||
|
||||
@@ -20,7 +20,7 @@ import gplx.core.primitives.*; import gplx.core.brys.*; import gplx.core.ios.*;
|
||||
import gplx.xowa.langs.*; import gplx.xowa.langs.msgs.*; import gplx.xowa.langs.cases.*;
|
||||
import gplx.xowa.wikis.*; import gplx.xowa.wikis.domains.*; import gplx.xowa.wikis.metas.*; import gplx.xowa.wikis.data.site_stats.*; import gplx.xowa.wikis.ttls.*; import gplx.xowa.wikis.data.*; import gplx.xowa.wikis.xwikis.*; import gplx.xowa.addons.*;
|
||||
import gplx.xowa.files.*; import gplx.xowa.files.repos.*; import gplx.xowa.files.origs.*; import gplx.xowa.files.bins.*; import gplx.fsdb.meta.*; import gplx.fsdb.*;
|
||||
import gplx.xowa.htmls.*; import gplx.xowa.htmls.core.htmls.utls.*; import gplx.xowa.htmls.core.hzips.*; import gplx.xowa.htmls.core.*; import gplx.xowa.htmls.bridges.dbuis.tbls.*; import gplx.xowa.htmls.hrefs.*; import gplx.xowa.addons.wikis.ctgs.htmls.pageboxs.*;
|
||||
import gplx.xowa.htmls.*; import gplx.xowa.htmls.core.htmls.utls.*; import gplx.xowa.htmls.core.hzips.*; import gplx.xowa.htmls.core.*; import gplx.xowa.htmls.bridges.dbuis.tbls.*; import gplx.xowa.htmls.hrefs.*; import gplx.xowa.addons.wikis.ctgs.htmls.pageboxs.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.xowa.parsers.*;
|
||||
import gplx.xowa.apps.urls.*;
|
||||
public interface Xow_wiki extends Xow_ttl_parser, Gfo_invk {
|
||||
@@ -46,7 +46,8 @@ public interface Xow_wiki extends Xow_ttl_parser, Gfo_invk {
|
||||
Xoh_page_wtr_mgr Html__wtr_mgr();
|
||||
Xoh_href_wtr Html__href_wtr();
|
||||
Xoh_lnki_bldr Html__lnki_bldr();
|
||||
Xoctg_pagebox_wtr Html__ctg_pagebox_wtr();
|
||||
Xoctg_pagebox_wtr Ctg__pagebox_wtr();
|
||||
Xoctg_catpage_mgr Ctg__catpage_mgr();
|
||||
boolean Html__css_installing(); void Html__css_installing_(boolean v);
|
||||
Xow_msg_mgr Msg_mgr();
|
||||
byte[] Wtxt__expand_tmpl(byte[] src);
|
||||
|
||||
@@ -29,7 +29,7 @@ import gplx.xowa.addons.wikis.ctgs.*;
|
||||
import gplx.xowa.guis.cbks.*; import gplx.xowa.guis.views.*;
|
||||
import gplx.xowa.xtns.gallery.*; import gplx.xowa.xtns.pfuncs.*;
|
||||
import gplx.xowa.wikis.tdbs.*; import gplx.xowa.wikis.tdbs.hives.*;
|
||||
import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.htmls.css.mgrs.*; import gplx.xowa.addons.wikis.ctgs.htmls.pageboxs.*;
|
||||
import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.htmls.css.mgrs.*; import gplx.xowa.addons.wikis.ctgs.htmls.pageboxs.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
public class Xowe_wiki implements Xow_wiki, Gfo_invk, Gfo_evt_itm {
|
||||
private boolean init_in_process = false;
|
||||
public Xowe_wiki(Xoae_app app, Xol_lang_itm lang, Xow_ns_mgr ns_mgr, Xow_domain_itm domain_itm, Io_url wiki_dir) {
|
||||
@@ -78,6 +78,7 @@ public class Xowe_wiki implements Xow_wiki, Gfo_invk, Gfo_evt_itm {
|
||||
cache_mgr = new Xow_cache_mgr(this);
|
||||
/*if (Bry_.Eq(domain_bry, Xow_domain_itm_.Bry__home))*/ xwiki_mgr.Add_by_atrs(domain_bry, domain_bry); // add full name to xwiki_mgr; needed for lookup in home ns; EX: [[home:Help/Contents]]
|
||||
this.lnki_bldr = new Xoh_lnki_bldr(app, href_wtr);
|
||||
this.ctg_catpage_mgr = new Xoctg_catpage_mgr(this);
|
||||
}
|
||||
public Gfo_evt_mgr Evt_mgr() {return ev_mgr;} private final Gfo_evt_mgr ev_mgr;
|
||||
public Xow_ns_mgr Ns_mgr() {return ns_mgr;} private final Xow_ns_mgr ns_mgr;
|
||||
@@ -105,7 +106,8 @@ public class Xowe_wiki implements Xow_wiki, Gfo_invk, Gfo_evt_itm {
|
||||
public Xoh_page_wtr_mgr Html__wtr_mgr() {return html_mgr.Page_wtr_mgr();}
|
||||
public Xoh_lnki_bldr Html__lnki_bldr() {return lnki_bldr;} private final Xoh_lnki_bldr lnki_bldr;
|
||||
public Xoh_href_wtr Html__href_wtr() {return href_wtr;} private final Xoh_href_wtr href_wtr = new Xoh_href_wtr();
|
||||
public Xoctg_pagebox_wtr Html__ctg_pagebox_wtr() {return ctg_pagebox_wtr;} private final Xoctg_pagebox_wtr ctg_pagebox_wtr = new Xoctg_pagebox_wtr();
|
||||
public Xoctg_pagebox_wtr Ctg__pagebox_wtr() {return ctg_pagebox_wtr;} private final Xoctg_pagebox_wtr ctg_pagebox_wtr = new Xoctg_pagebox_wtr();
|
||||
public Xoctg_catpage_mgr Ctg__catpage_mgr() {return ctg_catpage_mgr;} private final Xoctg_catpage_mgr ctg_catpage_mgr;
|
||||
public boolean Html__css_installing() {return html__css_installing;} public void Html__css_installing_(boolean v) {html__css_installing = v;} private boolean html__css_installing;
|
||||
public Xow_url_parser Utl__url_parser() {return url__parser;} private final Xow_url_parser url__parser;
|
||||
public Xow_mw_parser_mgr Mw_parser_mgr() {return mw_parser_mgr;} private final Xow_mw_parser_mgr mw_parser_mgr = new Xow_mw_parser_mgr();
|
||||
@@ -266,6 +268,7 @@ public class Xowe_wiki implements Xow_wiki, Gfo_invk, Gfo_evt_itm {
|
||||
else if (ctx.Match(k, Invk_maint)) return maint_mgr;
|
||||
else if (ctx.Match(k, Invk_domain)) return domain_str;
|
||||
else if (ctx.Match(k, Invk_xtns)) return xtn_mgr;
|
||||
else if (ctx.Match(k, Invk_catpage_mgr)) return ctg_catpage_mgr;
|
||||
else if (ctx.Match(k, Invk_hdump_enabled_)) this.html_mgr__hdump_enabled = m.ReadYn("v");
|
||||
else if (ctx.Match(k, gplx.xowa.apps.apis.xowa.wikis.langs.Xoap_lang_variants.Evt_current_changed)) lang.Vnt_mgr().Cur_itm_(m.ReadBry("v"));
|
||||
else return Gfo_invk_.Rv_unhandled;
|
||||
@@ -280,6 +283,7 @@ public class Xowe_wiki implements Xow_wiki, Gfo_invk, Gfo_evt_itm {
|
||||
, Invk_xtns = "xtns", Invk_import_mgr = "import"
|
||||
, Invk_db_mgr_to_sql_ = "db_mgr_to_sql_"
|
||||
, Invk_domain = "domain", Invk_maint = "maint", Invk_hdump_enabled_ = "hdump_enabled_"
|
||||
, Invk_catpage_mgr = "catpage_mgr"
|
||||
;
|
||||
public static final String Invk_db_mgr = "db_mgr"; // SERIALIZED:000.sqlite3|xowa_cfg
|
||||
public static final String Invk_lang_ = "lang_";
|
||||
|
||||
@@ -15,7 +15,7 @@ GNU Affero General Public License for more details.
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.bldrs.cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.bldrs.*;
|
||||
package gplx.xowa.addons.bldrs.app_cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*;
|
||||
import gplx.core.strings.*;
|
||||
public class Xoac_wiki_cfg_bldr_cmd {
|
||||
public Xoac_wiki_cfg_bldr_cmd(String key, String text) {this.key = key; this.text = text;}
|
||||
@@ -15,7 +15,7 @@ GNU Affero General Public License for more details.
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.bldrs.cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.bldrs.*;
|
||||
package gplx.xowa.addons.bldrs.app_cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*;
|
||||
public class Xoac_wiki_cfg_bldr_fil implements Gfo_invk {
|
||||
public Xoac_wiki_cfg_bldr_fil(String wiki) {this.wiki = wiki;}
|
||||
public String Wiki() {return wiki;} private String wiki;
|
||||
@@ -15,8 +15,9 @@ GNU Affero General Public License for more details.
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.bldrs.cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.bldrs.*;
|
||||
package gplx.xowa.addons.bldrs.app_cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*;
|
||||
import gplx.core.strings.*;
|
||||
import gplx.xowa.bldrs.*;
|
||||
public class Xob_wiki_cfg_bldr implements Gfo_invk {
|
||||
public Xob_wiki_cfg_bldr(Xob_bldr bldr) {this.app = bldr.App();} private Xoae_app app;
|
||||
public void Exec() {
|
||||
@@ -15,7 +15,7 @@ GNU Affero General Public License for more details.
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.bldrs.cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.bldrs.*;
|
||||
package gplx.xowa.addons.bldrs.app_cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*;
|
||||
import org.junit.*; import gplx.core.strings.*;
|
||||
public class Xob_wiki_cfg_bldr_tst {
|
||||
Xob_wiki_cfg_bldr_fxt fxt = new Xob_wiki_cfg_bldr_fxt();
|
||||
@@ -0,0 +1,31 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.bldrs.app_cfgs.wm_server_cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*; import gplx.xowa.addons.bldrs.app_cfgs.*;
|
||||
import gplx.xowa.bldrs.*; import gplx.xowa.bldrs.wkrs.*;
|
||||
public class Xowm_server_cfg_cmd extends Xob_cmd__base {
|
||||
public Xowm_server_cfg_cmd(Xob_bldr bldr, Xowe_wiki wiki) {super(bldr, wiki);}
|
||||
@Override public void Cmd_run() {
|
||||
// wiki.Init_assert();
|
||||
// mgr.Exec(wiki);
|
||||
}
|
||||
|
||||
public static final String BLDR_CMD_KEY = "cfg.wikis.wm_server_cfg";
|
||||
@Override public String Cmd_key() {return BLDR_CMD_KEY;}
|
||||
public static final Xob_cmd Prototype = new Xowm_server_cfg_cmd(null, null);
|
||||
@Override public Xob_cmd Cmd_clone(Xob_bldr bldr, Xowe_wiki wiki) {return new Xowm_server_cfg_cmd(bldr, wiki);}
|
||||
}
|
||||
@@ -0,0 +1,36 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.bldrs.app_cfgs.wm_server_cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*; import gplx.xowa.addons.bldrs.app_cfgs.*;
|
||||
import gplx.xowa.bldrs.*; import gplx.xowa.bldrs.wkrs.*;
|
||||
public class Xowm_server_cfg_mgr {
|
||||
public void Exec() {
|
||||
byte[] src = Load_or_download();
|
||||
Parse_cat_collation(src);
|
||||
}
|
||||
private byte[] Load_or_download() {
|
||||
// Io_mgr.Instance.DownloadFil_args("", Io_url_.NullPtr).Exec_as_bry("https://noc.wikimedia.org/conf/InitialiseSettings.php.txt");
|
||||
return null;
|
||||
}
|
||||
private void Parse_cat_collation(byte[] src) {
|
||||
int bgn_pos = Bry_find_.Find_fwd(src, Bry_.new_a7("wgCategoryCollation"));
|
||||
if (bgn_pos == Bry_find_.Not_found) throw Err_.new_wo_type("could not find wgCategoryCollation bgn");
|
||||
int end_pos = Bry_find_.Find_fwd(src, Bry_.new_a7("],"));
|
||||
if (end_pos == Bry_find_.Not_found) throw Err_.new_wo_type("could not find wgCategoryCollation end");
|
||||
Tfds.Write(src, bgn_pos, end_pos);
|
||||
}
|
||||
}
|
||||
@@ -54,4 +54,8 @@ public class Xobc_data_db {
|
||||
tbl__import_step.Delete(step_id);
|
||||
}
|
||||
}
|
||||
|
||||
public static Xobc_data_db New(gplx.xowa.apps.fsys.Xoa_fsys_mgr fsys_mgr) {
|
||||
return new Xobc_data_db(fsys_mgr.Bin_addon_dir().GenSubFil_nest("bldr", "central", "bldr_central.data_db.xowa"));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,32 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.bldrs.centrals.dbs.datas; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*; import gplx.xowa.addons.bldrs.centrals.*; import gplx.xowa.addons.bldrs.centrals.dbs.*;
|
||||
public class Xobc_task_regy_itm {
|
||||
public Xobc_task_regy_itm(int id, int seqn, byte[] key, byte[] name, int step_count) {
|
||||
this.id = id;
|
||||
this.seqn = seqn;
|
||||
this.key = key;
|
||||
this.name = name;
|
||||
this.step_count = step_count;
|
||||
}
|
||||
public int Id() {return id;} private final int id;
|
||||
public int Seqn() {return seqn;} private final int seqn;
|
||||
public byte[] Key() {return key;} private final byte[] key;
|
||||
public byte[] Name() {return name;} private final byte[] name;
|
||||
public int Step_count() {return step_count;} private final int step_count;
|
||||
}
|
||||
@@ -67,6 +67,28 @@ public class Xobc_task_regy_tbl implements Db_tbl {
|
||||
.Val_str(fld_task_key, task_key).Val_str(fld_task_name, task_name)
|
||||
.Exec_insert();
|
||||
}
|
||||
public Xobc_task_regy_itm[] Select_by_wiki(byte[] wiki_domain) {
|
||||
String sql = Db_sql_.Make_by_fmt(String_.Ary
|
||||
( "SELECT *"
|
||||
, "FROM task_regy"
|
||||
, "WHERE task_key LIKE '{0}%'"
|
||||
, "AND task_seqn != 999999"
|
||||
), wiki_domain);
|
||||
List_adp list = List_adp_.New();
|
||||
Db_rdr rdr = conn.Stmt_sql(sql).Exec_select__rls_auto();
|
||||
try {
|
||||
while (rdr.Move_next()) {
|
||||
list.Add(new Xobc_task_regy_itm
|
||||
( rdr.Read_int("task_id")
|
||||
, rdr.Read_int("task_seqn")
|
||||
, rdr.Read_bry_by_str("task_key")
|
||||
, rdr.Read_bry_by_str("task_name")
|
||||
, rdr.Read_int("step_count")
|
||||
));
|
||||
}
|
||||
} finally {rdr.Rls();}
|
||||
return (Xobc_task_regy_itm[])list.To_ary_and_clear(Xobc_task_regy_itm.class);
|
||||
}
|
||||
public void Delete(int task_id) {
|
||||
conn.Stmt_delete(tbl_name, fld_task_id).Crt_int(fld_task_id, task_id).Exec_delete();
|
||||
}
|
||||
|
||||
@@ -44,20 +44,7 @@ public class Xobc_import_step_tbl implements Db_tbl {
|
||||
Db_rdr rdr = conn.Stmt_select(tbl_name, flds, fld_step_id).Crt_int(fld_step_id, step_id).Exec_select__rls_auto();
|
||||
try {
|
||||
return (rdr.Move_next())
|
||||
? new Xobc_import_step_itm
|
||||
( rdr.Read_int(fld_step_id)
|
||||
, rdr.Read_int(fld_host_id)
|
||||
, rdr.Read_bry_by_str(fld_wiki_abrv)
|
||||
, rdr.Read_str(fld_wiki_date)
|
||||
, rdr.Read_str(fld_import_name)
|
||||
, rdr.Read_int(fld_import_type)
|
||||
, rdr.Read_byte(fld_import_zip)
|
||||
, rdr.Read_long(fld_import_size_zip)
|
||||
, rdr.Read_long(fld_import_size_raw)
|
||||
, rdr.Read_str(fld_import_md5)
|
||||
, rdr.Read_long(fld_prog_size_end)
|
||||
, rdr.Read_int(fld_prog_count_end)
|
||||
)
|
||||
? New_itm(rdr)
|
||||
: Xobc_import_step_itm.Null;
|
||||
}
|
||||
finally {rdr.Rls();}
|
||||
@@ -95,7 +82,39 @@ public class Xobc_import_step_tbl implements Db_tbl {
|
||||
}
|
||||
} finally {rdr.Rls();}
|
||||
}
|
||||
public Xobc_import_step_itm[] Select_by_task_id(int task_id) {
|
||||
List_adp list = List_adp_.New();
|
||||
Db_rdr rdr = conn.Stmt_sql(Db_sql_.Make_by_fmt(String_.Ary
|
||||
( "SELECT s.*"
|
||||
, "FROM import_step s"
|
||||
, " JOIN step_map sm ON s.step_id = sm.step_id"
|
||||
, "WHERE sm.task_id = {0}"
|
||||
), task_id))
|
||||
.Exec_select__rls_auto();
|
||||
try {
|
||||
while (rdr.Move_next()) {
|
||||
list.Add(New_itm(rdr));
|
||||
}
|
||||
} finally {rdr.Rls();}
|
||||
return (Xobc_import_step_itm[])list.To_ary_and_clear(Xobc_import_step_itm.class);
|
||||
}
|
||||
public void Rls() {
|
||||
insert_stmt = Db_stmt_.Rls(insert_stmt);
|
||||
}
|
||||
private Xobc_import_step_itm New_itm(Db_rdr rdr) {
|
||||
return new Xobc_import_step_itm
|
||||
( rdr.Read_int(fld_step_id)
|
||||
, rdr.Read_int(fld_host_id)
|
||||
, rdr.Read_bry_by_str(fld_wiki_abrv)
|
||||
, rdr.Read_str(fld_wiki_date)
|
||||
, rdr.Read_str(fld_import_name)
|
||||
, rdr.Read_int(fld_import_type)
|
||||
, rdr.Read_byte(fld_import_zip)
|
||||
, rdr.Read_long(fld_import_size_zip)
|
||||
, rdr.Read_long(fld_import_size_raw)
|
||||
, rdr.Read_str(fld_import_md5)
|
||||
, rdr.Read_long(fld_prog_size_end)
|
||||
, rdr.Read_int(fld_prog_count_end)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,7 +19,7 @@ package gplx.xowa.addons.bldrs.exports.packs.files; import gplx.*; import gplx.x
|
||||
import gplx.core.progs.*; import gplx.core.ios.zips.*; import gplx.core.ios.streams.*; import gplx.core.security.*;
|
||||
import gplx.dbs.*; import gplx.xowa.wikis.data.*; import gplx.fsdb.*; import gplx.fsdb.meta.*;
|
||||
import gplx.xowa.addons.bldrs.centrals.dbs.*; import gplx.xowa.addons.bldrs.centrals.dbs.datas.*; import gplx.xowa.addons.bldrs.centrals.dbs.datas.imports.*; import gplx.xowa.addons.bldrs.centrals.steps.*; import gplx.xowa.addons.bldrs.centrals.hosts.*;
|
||||
class Pack_file_mgr {
|
||||
public class Pack_file_mgr {
|
||||
public void Exec(Xowe_wiki wiki, Pack_file_bldr_cfg cfg) {
|
||||
// init
|
||||
wiki.Init_assert();
|
||||
@@ -31,7 +31,7 @@ class Pack_file_mgr {
|
||||
|
||||
// get import_tbl
|
||||
byte[] wiki_abrv = wiki.Domain_itm().Abrv_xo();
|
||||
Xobc_data_db bc_db = new Xobc_data_db(wiki.App().Fsys_mgr().Bin_addon_dir().GenSubFil_nest("bldr", "central", "bldr_central.data_db.xowa"));
|
||||
Xobc_data_db bc_db = Xobc_data_db.New(wiki.App().Fsys_mgr());
|
||||
Db_conn bc_conn = bc_db.Conn();
|
||||
bc_db.Delete_by_import(wiki_abrv, wiki_date);
|
||||
bc_conn.Txn_bgn("xobc_import_insert");
|
||||
@@ -93,7 +93,7 @@ class Pack_file_mgr {
|
||||
int pack_list_len = pack_list.Len();
|
||||
|
||||
// create task
|
||||
String task_key = wiki.Domain_str() + "|" + wiki_date + "|" + task_type;
|
||||
String task_key = Task_key__build(wiki.Domain_str(), wiki_date, task_type);
|
||||
String task_name = Build_task_name(tmp_bfr, wiki, wiki_date, task_type, raw_len);
|
||||
Xobc_task_regy_tbl task_regy_tbl = bc_db.Tbl__task_regy();
|
||||
int task_id = bc_db.Conn().Sys_mgr().Autonum_next("task_regy.task_id");
|
||||
@@ -161,6 +161,12 @@ class Pack_file_mgr {
|
||||
bc_db.Tbl__step_regy().Insert(step_id, Xobc_step_itm.Type__wiki_import);
|
||||
bc_db.Tbl__import_step().Insert(step_id, gplx.xowa.addons.bldrs.centrals.dbs.datas.Xobc_host_regy_tbl.Host_id__archive_org, wiki_abrv, wiki_date, zip_url.NameAndExt(), itm.Tid(), Xobc_zip_type.Type__zip, zip_md5, zip_len, raw_size, 0, 0);
|
||||
}
|
||||
private static String Task_key__build(String wiki_domain, String wiki_date, String task_type) {
|
||||
return String_.Concat(wiki_domain, "|", wiki_date, "|", task_type);
|
||||
}
|
||||
public static String[] Task_key__parse(String task_key) {
|
||||
return String_.Split(task_key, "|");
|
||||
}
|
||||
}
|
||||
class Pack_hash_bldr {
|
||||
public static Pack_hash Bld(Xow_wiki wiki, Io_url wiki_dir, Io_url pack_dir, String wiki_date, boolean pack_html, boolean pack_file, DateAdp pack_file_cutoff, boolean pack_fsdb_delete) {
|
||||
|
||||
@@ -33,7 +33,7 @@ class Pack_mgr {
|
||||
|
||||
// get import_tbl
|
||||
byte[] wiki_abrv = wiki.Domain_itm().Abrv_xo();
|
||||
Xobc_data_db bc_db = new Xobc_data_db(wiki.App().Fsys_mgr().Bin_addon_dir().GenSubFil_nest("bldr", "central", "bldr_central.data_db.xowa"));
|
||||
Xobc_data_db bc_db = Xobc_data_db.New(wiki.App().Fsys_mgr());
|
||||
Db_conn bc_conn = bc_db.Conn();
|
||||
bc_db.Delete_by_import(wiki_abrv, wiki_date);
|
||||
bc_conn.Txn_bgn("xobc_import_insert");
|
||||
|
||||
@@ -19,6 +19,8 @@ package gplx.xowa.addons.bldrs.files; import gplx.*; import gplx.xowa.*; import
|
||||
import gplx.xowa.bldrs.wkrs.*;
|
||||
import gplx.xowa.addons.bldrs.files.cmds.*;
|
||||
import gplx.xowa.addons.bldrs.mass_parses.inits.*; import gplx.xowa.addons.bldrs.mass_parses.parses.*; import gplx.xowa.addons.bldrs.mass_parses.makes.*;
|
||||
import gplx.xowa.addons.bldrs.files.cksums.*;
|
||||
import gplx.xowa.addons.bldrs.app_cfgs.wm_server_cfgs.*;
|
||||
public class Xoax_builds_files_addon implements Xoax_addon_itm, Xoax_addon_itm__bldr {
|
||||
public Xob_cmd[] Bldr_cmds() {
|
||||
return new Xob_cmd[]
|
||||
@@ -43,6 +45,9 @@ public class Xoax_builds_files_addon implements Xoax_addon_itm, Xoax_addon_itm__
|
||||
, Xomp_init_cmd.Prototype
|
||||
, Xomp_parse_cmd.Prototype
|
||||
, Xomp_make_cmd.Prototype
|
||||
, Xocksum_calc_cmd.Prototype
|
||||
|
||||
, Xowm_server_cfg_cmd.Prototype
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.bldrs.files.cksums; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*; import gplx.xowa.addons.bldrs.files.*;
|
||||
import gplx.xowa.bldrs.*; import gplx.xowa.bldrs.wkrs.*;
|
||||
public class Xocksum_calc_cmd extends Xob_cmd__base {
|
||||
public Xocksum_calc_cmd(Xob_bldr bldr, Xowe_wiki wiki) {super(bldr, wiki);}
|
||||
@Override public void Cmd_run() {
|
||||
wiki.Init_assert();
|
||||
new Xocksum_calc_mgr().Exec(wiki);
|
||||
}
|
||||
|
||||
@Override public String Cmd_key() {return BLDR_CMD_KEY;} private static final String BLDR_CMD_KEY = "fsdb.cksums.calc";
|
||||
public static final Xob_cmd Prototype = new Xocksum_calc_cmd(null, null);
|
||||
@Override public Xob_cmd Cmd_clone(Xob_bldr bldr, Xowe_wiki wiki) {return new Xocksum_calc_cmd(bldr, wiki);}
|
||||
}
|
||||
@@ -0,0 +1,79 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.bldrs.files.cksums; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*; import gplx.xowa.addons.bldrs.files.*;
|
||||
import gplx.core.ios.streams.*; import gplx.core.security.*;
|
||||
import gplx.dbs.*; import gplx.xowa.addons.bldrs.files.cksums.dbs.*;
|
||||
import gplx.xowa.files.*; import gplx.fsdb.*; import gplx.fsdb.data.*;
|
||||
public class Xocksum_calc_mgr {
|
||||
public void Exec(Xowe_wiki wiki) {
|
||||
// get conn variables
|
||||
Xocksum_cksum_db db = Xocksum_cksum_db.Get(wiki);
|
||||
Db_conn conn = db.Conn();
|
||||
Xocksum_cksum_tbl tbl = db.Tbl__cksum();
|
||||
conn.Meta_tbl_assert(tbl);
|
||||
|
||||
// insert missing items
|
||||
tbl.Insert_missing();
|
||||
tbl.Create_idx();
|
||||
|
||||
// get updates
|
||||
int count = 0;
|
||||
Hash_algo md5_algo = Hash_algo_.New__md5();
|
||||
List_adp updates = List_adp_.New();
|
||||
String cur_date = Datetime_now.Get().XtoStr_gplx();
|
||||
Db_stmt select_stmt = tbl.Select_samples_stmt(10000);
|
||||
while (true) {
|
||||
// get cksum_rows
|
||||
Xocksum_cksum_row[] rows = tbl.Select_samples(select_stmt);
|
||||
|
||||
// loop cksum_rows and (a) get bin_data; (b) if md5 diff, then add to updates
|
||||
int len = rows.length; if (len == 0) break;
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Xocksum_cksum_row row = rows[i];
|
||||
byte[] bin_bry = Get_bin(wiki, row);
|
||||
if (bin_bry == null) {
|
||||
Gfo_usr_dlg_.Instance.Prog_many("", "", "null; fil_id=~{0} thm_id=~{1}", row.Fil_id(), row.Thm_id());
|
||||
bin_bry = Bry_.Empty;
|
||||
}
|
||||
row.Bin_size_(bin_bry.length);
|
||||
byte[] md5 = md5_algo.Hash_bry_as_bry(bin_bry);
|
||||
if (!Bry_.Eq(md5, row.Cksum_val())) {
|
||||
row.Cksum_val_(md5);
|
||||
updates.Add(row);
|
||||
}
|
||||
}
|
||||
|
||||
// run updates
|
||||
conn.Txn_bgn("cksum_update");
|
||||
len = updates.Len();
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Xocksum_cksum_row row = (Xocksum_cksum_row)updates.Get_at(i);
|
||||
tbl.Update(row.Fil_id(), row.Thm_id(), row.Bin_db_id(), row.Bin_size(), row.Cksum_tid(), 0, row.Cksum_val(), cur_date);
|
||||
if (++count % 2000 == 0) Gfo_usr_dlg_.Instance.Prog_many("", "", "updating; rows=~{0}", count);
|
||||
}
|
||||
updates.Clear();
|
||||
conn.Txn_end();
|
||||
}
|
||||
select_stmt.Rls();
|
||||
}
|
||||
private byte[] Get_bin(Xowe_wiki wiki, Xocksum_cksum_row row) {
|
||||
int bin_id = row.Thm_id() == -1 ? row.Fil_id() : row.Thm_id();
|
||||
Fsd_bin_itm bin_itm = wiki.File__mnt_mgr().Mnts__get_main().Bin_mgr().Dbs__get_at(row.Bin_db_id()).Select_as_itm(bin_id);
|
||||
return bin_itm.Bin_data();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,31 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.bldrs.files.cksums.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*; import gplx.xowa.addons.bldrs.files.*; import gplx.xowa.addons.bldrs.files.cksums.*;
|
||||
import gplx.dbs.*; import gplx.fsdb.meta.*;
|
||||
public class Xocksum_cksum_db {
|
||||
public Xocksum_cksum_db(Db_conn conn) {
|
||||
this.conn = conn;
|
||||
this.tbl__cksum = new Xocksum_cksum_tbl(conn);
|
||||
}
|
||||
public Db_conn Conn() {return conn;} private final Db_conn conn;
|
||||
public Xocksum_cksum_tbl Tbl__cksum() {return tbl__cksum;} private final Xocksum_cksum_tbl tbl__cksum;
|
||||
|
||||
public static Xocksum_cksum_db Get(Xowe_wiki wiki) {
|
||||
return new Xocksum_cksum_db(wiki.File__fsdb_core().File__abc_file__at(Fsm_mnt_mgr.Mnt_idx_main).Conn());
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.bldrs.files.cksums.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*; import gplx.xowa.addons.bldrs.files.*; import gplx.xowa.addons.bldrs.files.cksums.*;
|
||||
public class Xocksum_cksum_row {
|
||||
public Xocksum_cksum_row(int fil_id, int thm_id, int bin_db_id, long bin_size, byte cksum_tid, int cksum_count, byte[] cksum_val, String cksum_date) {
|
||||
this.fil_id = fil_id;
|
||||
this.thm_id = thm_id;
|
||||
this.bin_db_id = bin_db_id;
|
||||
this.bin_size = bin_size;
|
||||
this.cksum_tid = cksum_tid;
|
||||
this.cksum_count = cksum_count;
|
||||
this.cksum_val = cksum_val;
|
||||
this.cksum_date = cksum_date;
|
||||
}
|
||||
public int Fil_id() {return fil_id;} private final int fil_id;
|
||||
public int Thm_id() {return thm_id;} private final int thm_id;
|
||||
public int Bin_db_id() {return bin_db_id;} private final int bin_db_id;
|
||||
public long Bin_size() {return bin_size;} private long bin_size;
|
||||
public byte Cksum_tid() {return cksum_tid;} private final byte cksum_tid;
|
||||
public int Cksum_count() {return cksum_count;} private final int cksum_count;
|
||||
public byte[] Cksum_val() {return cksum_val;} private byte[] cksum_val;
|
||||
public String Cksum_date() {return cksum_date;} private final String cksum_date;
|
||||
|
||||
public void Bin_size_(long v) {this.bin_size = v;}
|
||||
public void Cksum_val_(byte[] v) {this.cksum_val = v;}
|
||||
}
|
||||
@@ -0,0 +1,107 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.bldrs.files.cksums.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.bldrs.*; import gplx.xowa.addons.bldrs.files.*; import gplx.xowa.addons.bldrs.files.cksums.*;
|
||||
import gplx.dbs.*; import gplx.dbs.qrys.*; import gplx.xowa.addons.wikis.ctgs.*;
|
||||
public class Xocksum_cksum_tbl implements Db_tbl {
|
||||
private final Dbmeta_fld_list flds = new Dbmeta_fld_list();
|
||||
private final String fld__fil_id, fld__thm_id, fld__bin_db_id, fld__bin_len, fld__cksum_tid, fld__cksum_count, fld__cksum_val, fld__cksum_date;
|
||||
private Db_stmt stmt__update;
|
||||
public Xocksum_cksum_tbl(Db_conn conn) {
|
||||
this.conn = conn;
|
||||
this.tbl_name = "fsdb_cksum";
|
||||
this.fld__fil_id = flds.Add_int("fil_id");
|
||||
this.fld__thm_id = flds.Add_int("thm_id");
|
||||
this.fld__bin_db_id = flds.Add_int("bin_db_id");
|
||||
this.fld__bin_len = flds.Add_long("bin_size");
|
||||
this.fld__cksum_tid = flds.Add_byte("cksum_tid");
|
||||
this.fld__cksum_count = flds.Add_int("cksum_count");
|
||||
this.fld__cksum_val = flds.Add_str("cksum_val", 255);
|
||||
this.fld__cksum_date = flds.Add_str("cksum_date", 16);
|
||||
conn.Rls_reg(this);
|
||||
}
|
||||
public Db_conn Conn() {return conn;} private final Db_conn conn;
|
||||
public String Tbl_name() {return tbl_name;} private final String tbl_name;
|
||||
public void Create_tbl() {conn.Meta_tbl_create(Dbmeta_tbl_itm.New(tbl_name, flds));}
|
||||
public void Create_idx() {
|
||||
conn.Meta_idx_create(Dbmeta_idx_itm.new_normal_by_tbl(tbl_name, "fil_id__thm_id", fld__fil_id, fld__thm_id));
|
||||
conn.Meta_idx_create(Dbmeta_idx_itm.new_normal_by_tbl(tbl_name, fld__cksum_val, fld__cksum_val));
|
||||
}
|
||||
public void Insert_missing() {
|
||||
// insert from fsdb_fil
|
||||
conn.Exec_sql(Db_sql_.Make_by_fmt(String_.Ary
|
||||
( "INSERT INTO fsdb_cksum (fil_id, thm_id, bin_db_id, bin_size, cksum_tid, cksum_count, cksum_val, cksum_date)"
|
||||
, "SELECT f.fil_id, -1, f.fil_bin_db_id, f.fil_size, {0}, 0, '', ''"
|
||||
, "FROM fsdb_fil f"
|
||||
, " LEFT JOIN fsdb_cksum c ON c.fil_id = f.fil_id AND c.thm_id = -1"
|
||||
, "WHERE c.fil_id IS NULL"
|
||||
, "AND f.fil_bin_db_id != -1"
|
||||
), Cksum_tid__md5));
|
||||
|
||||
// insert from fsdb_fil
|
||||
conn.Exec_sql(Db_sql_.Make_by_fmt(String_.Ary
|
||||
( "INSERT INTO fsdb_cksum (fil_id, thm_id, bin_db_id, bin_size, cksum_tid, cksum_count, cksum_val, cksum_date)"
|
||||
, "SELECT t.thm_owner_id, t.thm_id, t.thm_bin_db_id, t.thm_size, {0}, 0, '', ''"
|
||||
, "FROM fsdb_thm t"
|
||||
, " LEFT JOIN fsdb_cksum c ON c.fil_id = t.thm_owner_id AND c.thm_id = t.thm_id"
|
||||
, "WHERE c.fil_id IS NULL"
|
||||
), Cksum_tid__md5));
|
||||
}
|
||||
public Db_stmt Select_samples_stmt(int count) {
|
||||
return conn.Stmt_sql(Db_sql_.Make_by_fmt(String_.Ary
|
||||
( "SELECT *"
|
||||
, "FROM fsdb_cksum"
|
||||
, "WHERE cksum_val = ''"
|
||||
// , "ORDER BY cksum_count, cksum_date"
|
||||
, "LIMIT {0}"
|
||||
), count));
|
||||
}
|
||||
public Xocksum_cksum_row[] Select_samples(Db_stmt stmt) {
|
||||
List_adp rv = List_adp_.New();
|
||||
|
||||
Db_rdr rdr = stmt.Exec_select__rls_manual();
|
||||
try {
|
||||
while (rdr.Move_next()) {
|
||||
rv.Add(new Xocksum_cksum_row
|
||||
( rdr.Read_int("fil_id")
|
||||
, rdr.Read_int("thm_id")
|
||||
, rdr.Read_int("bin_db_id")
|
||||
, rdr.Read_long("bin_size")
|
||||
, rdr.Read_byte("cksum_tid")
|
||||
, rdr.Read_int("cksum_count")
|
||||
, rdr.Read_bry_by_str("cksum_val")
|
||||
, rdr.Read_str("cksum_date")
|
||||
));
|
||||
}
|
||||
} finally {rdr.Rls();}
|
||||
|
||||
return (Xocksum_cksum_row[])rv.To_ary_and_clear(Xocksum_cksum_row.class);
|
||||
}
|
||||
public void Update(int fil_id, int thm_id, int bin_db_id, long bin_size, byte cksum_tid, int cksum_count, byte[] cksum_val, String cksum_date) {
|
||||
if (stmt__update == null) stmt__update = conn.Stmt_update_exclude(tbl_name, flds, fld__fil_id, fld__thm_id);
|
||||
stmt__update.Clear()
|
||||
.Val_int(fld__bin_db_id, bin_db_id).Val_long(fld__bin_len, bin_size)
|
||||
.Val_byte(fld__cksum_tid, cksum_tid).Val_int(fld__cksum_count, cksum_count)
|
||||
.Val_bry_as_str(fld__cksum_val, cksum_val).Val_str(fld__cksum_date, cksum_date)
|
||||
.Crt_int(fld__fil_id, fil_id).Crt_int(fld__thm_id, thm_id)
|
||||
.Exec_update();
|
||||
}
|
||||
public void Rls() {
|
||||
this.stmt__update = Db_stmt_.Rls(stmt__update);
|
||||
}
|
||||
public static final byte Cksum_tid__md5 = 1;
|
||||
}
|
||||
@@ -39,7 +39,7 @@ class Hdump_html_loader {
|
||||
html_db.Tbl__html().Select_by_page(tmp_hpg);
|
||||
|
||||
// unzip it
|
||||
byte[] html_hzip = stream_zip_mgr.Unzip(Io_stream_.Tid_gzip, tmp_hpg.Db().Html().Html_bry());
|
||||
byte[] html_hzip = stream_zip_mgr.Unzip(Io_stream_tid_.Tid__gzip, tmp_hpg.Db().Html().Html_bry());
|
||||
return wiki.Html__hdump_mgr().Load_mgr().Decode_as_bry(tmp_bfr, tmp_hpg, html_hzip, true);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -31,7 +31,7 @@ public class Xomp_parse_mgr_cfg implements Gfo_invk {
|
||||
public boolean Log_file_lnkis() {return log_file_lnkis;} private boolean log_file_lnkis = true;
|
||||
public boolean Load_all_templates() {return load_all_templates;} private boolean load_all_templates = true;
|
||||
public boolean Load_all_imglnks() {return load_all_imglnks;} private boolean load_all_imglnks = true;
|
||||
public byte Zip_tid() {return zip_tid;} private byte zip_tid = Io_stream_.Tid_gzip;
|
||||
public byte Zip_tid() {return zip_tid;} private byte zip_tid = Io_stream_tid_.Tid__gzip;
|
||||
public Io_url Mgr_url() {return mgr_url;} private Io_url mgr_url;
|
||||
public String Wkr_machine_name() {return wkr_machine_name;} private String wkr_machine_name;
|
||||
public boolean Show_msg__fetched_pool() {return show_msg__fetched_pool;} private boolean show_msg__fetched_pool;
|
||||
|
||||
@@ -32,7 +32,7 @@ class Xodel_make_mgr {
|
||||
, "FROM xfer_regy xr"
|
||||
, "WHERE xr.lnki_ttl = fsdb_regy.fsdb_name"
|
||||
, "AND xr.file_is_orig = fsdb_regy.fsdb_is_orig"
|
||||
, "AND xr.orig_repo = fsdb_regy.fsdb_repo"
|
||||
// , "AND xr.orig_repo = fsdb_regy.fsdb_repo" // TOMBSTONE: do no reinstate; some images exist in both repos, and this will delete images from one repo; DATE:2016-09-28
|
||||
, "AND xr.file_w = fsdb_regy.fsdb_w"
|
||||
, "AND xr.lnki_time = fsdb_regy.fsdb_time"
|
||||
, "AND xr.lnki_page = fsdb_regy.fsdb_page"
|
||||
|
||||
@@ -0,0 +1,59 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.htmls.includes; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.htmls.*;
|
||||
import java.io.FileReader;
|
||||
|
||||
import javax.script.Invocable;
|
||||
import javax.script.ScriptEngine;
|
||||
import javax.script.ScriptEngineManager;
|
||||
class Script_engine__java implements Script_engine {
|
||||
private final ScriptEngine engine;
|
||||
private final Invocable invk;
|
||||
public Script_engine__java() {
|
||||
ScriptEngineManager manager = new ScriptEngineManager();
|
||||
this.engine = manager.getEngineByName("JavaScript");
|
||||
this.invk = (Invocable)engine;
|
||||
}
|
||||
public void Load_script(Io_url url) {
|
||||
try {
|
||||
engine.eval(new FileReader(url.Xto_api()));
|
||||
// return engine.eval(script);
|
||||
} catch (Exception e) {
|
||||
System.out.println(e);
|
||||
}
|
||||
}
|
||||
public void Put_object(String key, Object val) {
|
||||
engine.put(key, val);
|
||||
}
|
||||
public Object Get_object(String obj_name) {
|
||||
try {
|
||||
return engine.get(obj_name);
|
||||
} catch (Exception e) {
|
||||
System.out.println(e);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
public Object Invoke_method(Object obj, String func, Object... args) {
|
||||
try {
|
||||
return invk.invokeMethod(obj, func, args);
|
||||
} catch (Exception e) {
|
||||
System.out.println(e);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.htmls.includes; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.htmls.*;
|
||||
interface Script_engine {
|
||||
void Load_script(Io_url url);
|
||||
Object Get_object(String obj_name);
|
||||
void Put_object(String name, Object obj);
|
||||
Object Invoke_method(Object obj, String func, Object... args);
|
||||
}
|
||||
class Script_engine__noop implements Script_engine {
|
||||
public void Load_script(Io_url url) {}
|
||||
public Object Get_object(String obj_name) {return null;}
|
||||
public void Put_object(String name, Object obj) {}
|
||||
public Object Invoke_method(Object obj, String func, Object... args) {return null;}
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.htmls.includes; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.htmls.*;
|
||||
import gplx.xowa.wikis.pages.tags.*;
|
||||
public class Xoh_include_mgr {
|
||||
private Io_url[] main_urls; private int main_urls_len;
|
||||
public void Init(Xow_wiki wiki) {
|
||||
// check bin dir
|
||||
Io_url include_dir = wiki.Fsys_mgr().Root_dir().GenSubDir_nest("bin", "html", "include");
|
||||
if (!Io_mgr.Instance.ExistsDir(include_dir)) return;
|
||||
|
||||
this.main_urls = Io_mgr.Instance.QueryDir_args(include_dir).FilPath_("*.js").ExecAsUrlAry();
|
||||
this.main_urls_len = main_urls.length;
|
||||
if (main_urls_len == 0) {
|
||||
Gfo_usr_dlg_.Instance.Warn_many("", "", "no '.js' files found; dir=~{0}", include_dir.Raw());
|
||||
return;
|
||||
}
|
||||
}
|
||||
public void Write(Xow_wiki wiki, Xoa_page page) {
|
||||
this.Init(wiki);
|
||||
if (main_urls_len == 0) return;
|
||||
|
||||
// create engine and load scripts
|
||||
Script_engine engine = new Script_engine__java();
|
||||
for (int i = 0; i < main_urls_len; ++i) {
|
||||
engine.Load_script(main_urls[i]);
|
||||
}
|
||||
// engine.Put_object("page", new Xoscript_page())
|
||||
Xoscript_page xos_pg = new Xoscript_page();
|
||||
|
||||
Object xowa_script = engine.Get_object("xowa_script");
|
||||
// engine.Invoke_method(xowa_script, "main", page.Url().To_str());
|
||||
engine.Invoke_method(xowa_script, "main", xos_pg);
|
||||
// if (String_.Has(rv, "yes")) {
|
||||
// Io_url js_url = null;
|
||||
// page.Html_data().Custom_head_tags().Add(Xopg_tag_itm.New_js_file(js_url));
|
||||
// }
|
||||
}
|
||||
// public static Xoh_include_mgr Get_or_new(Xow_wiki wiki) {
|
||||
// wiki.Addon_mgr().Itms__get_or_null();
|
||||
// }
|
||||
}
|
||||
@@ -0,0 +1,24 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.htmls.includes; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.htmls.*;
|
||||
public class Xoscript_page {
|
||||
private Xoscript_page_doc doc = new Xoscript_page_doc();
|
||||
public Xoscript_page_doc Doc() {
|
||||
return doc;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.htmls.includes; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.htmls.*;
|
||||
public class Xoscript_page_doc {
|
||||
public void Test() {
|
||||
Tfds.Write("hi");
|
||||
}
|
||||
}
|
||||
@@ -19,12 +19,10 @@ package gplx.xowa.addons.wikis.ctgs.bldrs; import gplx.*; import gplx.xowa.*; im
|
||||
import gplx.dbs.*; import gplx.xowa.addons.wikis.ctgs.dbs.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.enums.*;
|
||||
import gplx.xowa.wikis.data.*; import gplx.xowa.wikis.data.tbls.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.bldrs.ucas.*;
|
||||
class Xob_catlink_mgr {
|
||||
private Xowe_wiki wiki;
|
||||
private Xodb_tmp_cat_db tmp_db; private Db_conn tmp_conn; private Xodb_tmp_cat_link_tbl tmp_link_tbl;
|
||||
private final Xoctg_collation_enum collation_enum = new Xoctg_collation_enum(); private final Xoctg_type_enum type_enum = new Xoctg_type_enum();
|
||||
private Uca_trie trie; private final Bry_bfr uca_bfr = Bry_bfr_.New();
|
||||
private int rows = 0;
|
||||
public void On_cmd_bgn(Xowe_wiki wiki) {
|
||||
this.wiki = wiki;
|
||||
@@ -42,17 +40,13 @@ class Xob_catlink_mgr {
|
||||
byte collation_id = collation_enum.To_tid_or_fail(collation_bry);
|
||||
byte type_id = type_enum.To_tid_or_fail(type_bry);
|
||||
|
||||
// sortkey; handle \n
|
||||
// sortkey
|
||||
byte[] sortkey_actl = sortkey_orig;
|
||||
int nl_pos = Bry_find_.Find_fwd(sortkey_actl, Byte_ascii.Nl);
|
||||
if (nl_pos != Bry_find_.Not_found) // some sortkeys have format of "sortkey\ntitle"; discard 2nd to conserve hard-disk space; EX: "WALES, JIMMY\nJIMMY WALES"
|
||||
sortkey_actl = Bry_.Mid(sortkey_actl, 0, nl_pos); // NOTE: some sortkeys have space which will sort under " "; EX: ' \nART' -> " "; SEE: s.w:Category:Art
|
||||
|
||||
// sortkey; handle uca
|
||||
if (collation_id == Xoctg_collation_enum.Tid__uca) {
|
||||
if (trie == null) trie = new Uca_trie();
|
||||
trie.Decode(uca_bfr, sortkey_actl, 0, sortkey_actl.length);
|
||||
sortkey_actl = uca_bfr.Len() == 0 ? Byte_ascii.Space_bry : uca_bfr.To_bry_and_clear();
|
||||
if (collation_id != Xoctg_collation_enum.Tid__uca) {
|
||||
// sortkey; handle \n
|
||||
int nl_pos = Bry_find_.Find_fwd(sortkey_actl, Byte_ascii.Nl);
|
||||
if (nl_pos != Bry_find_.Not_found) // some sortkeys have format of "sortkey\ntitle"; discard 2nd to conserve hard-disk space; EX: "WALES, JIMMY\nJIMMY WALES"
|
||||
sortkey_actl = Bry_.Mid(sortkey_actl, 0, nl_pos); // NOTE: some sortkeys have space which will sort under " "; EX: ' \nART' -> " "; SEE: s.w:Category:Art
|
||||
}
|
||||
|
||||
// insert to tmp; notify; commit
|
||||
@@ -76,12 +70,12 @@ class Xob_catlink_mgr {
|
||||
}
|
||||
|
||||
// create tbl
|
||||
Xodb_cat_sort_tbl cat_sort_tbl = new Xodb_cat_sort_tbl(cat_core_conn);
|
||||
cat_core_conn.Meta_tbl_remake(cat_sort_tbl);
|
||||
cat_sort_tbl.Insert_by_select(tmp_conn);
|
||||
// Xodb_cat_sort_tbl cat_sort_tbl = new Xodb_cat_sort_tbl(cat_core_conn);
|
||||
// cat_core_conn.Meta_tbl_remake(cat_sort_tbl);
|
||||
// cat_sort_tbl.Insert_by_select(tmp_conn);
|
||||
|
||||
// make catlink_dbs
|
||||
cat_sort_tbl.Create_idx__key(); // index will be needed for join
|
||||
// cat_sort_tbl.Create_idx__key(); // index will be needed for join
|
||||
tmp_link_tbl.Create_idx__to_ttl(); // index will be needed for join
|
||||
Db_conn page_conn = wiki.Data__core_mgr().Db__core().Conn();
|
||||
Xob_catlink_wkr wkr = new Xob_catlink_wkr();
|
||||
@@ -92,7 +86,7 @@ class Xob_catlink_mgr {
|
||||
wkr.Update_page_cat_db_id(wiki, page_conn);
|
||||
|
||||
// cleanup
|
||||
cat_sort_tbl.Delete_idx__key(); // remove idx
|
||||
// cat_sort_tbl.Delete_idx__key(); // remove idx
|
||||
tmp_db.Delete();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -26,16 +26,16 @@ class Xob_catlink_wkr {
|
||||
( "SELECT tcl.cl_from"
|
||||
, ", p.page_id"
|
||||
, ", tcl.cl_type_id"
|
||||
, ", cs.cs_id"
|
||||
, ", tcl.cl_timestamp"
|
||||
, ", tcl.cl_sortkey"
|
||||
, ", tcl.cl_sortkey_prefix"
|
||||
, "FROM <temp_db>tmp_cat_link tcl"
|
||||
, " JOIN <cat_db>cat_sort cs ON tcl.cl_sortkey = cs.cs_key"
|
||||
, " JOIN page p ON p.page_namespace = 14 AND tcl.cl_to_ttl = p.page_title"
|
||||
, " JOIN page p ON p.page_namespace = 14 AND tcl.cl_to_ttl = p.page_title"
|
||||
, "ORDER BY 1" // NOTE: must sort by page_id to keep all cats for page in one db
|
||||
));
|
||||
attach_mgr.Attach();
|
||||
|
||||
// select from tmp_db and insert insert into cat_link
|
||||
// select from tmp_db and insert into cat_link
|
||||
Xodb_cat_link_tbl cat_link_tbl = Make_cat_link_tbl(wiki, null);
|
||||
Db_rdr rdr = attach_mgr.Conn_main().Stmt_sql(sql).Exec_select__rls_auto();
|
||||
try {
|
||||
@@ -46,7 +46,9 @@ class Xob_catlink_wkr {
|
||||
while (rdr.Move_next()) {
|
||||
// check if row can fit in db; else update db_size
|
||||
int page_id_cur = rdr.Read_int("cl_from");
|
||||
long db_size_new = db_size_cur + 46;// 46 = 3 ints (12) + 1 long (8) + 1 byte (2?) + 2 index (24?) + 9 fudge factor (?); DATE:2016-09-06
|
||||
byte[] sortkey = rdr.Read_bry("cl_sortkey");
|
||||
byte[] sortkey_prefix = rdr.Read_bry_by_str("cl_sortkey_prefix");
|
||||
long db_size_new = db_size_cur + 48 + (sortkey.length * 2) + sortkey_prefix.length;// 46 = 3 ints (12) + 1 long (8) + 1 byte (2?) + 2 index (24?) + 11 fudge factor (?); DATE:2016-09-06
|
||||
if ( db_size_cur > db_size_max // size exceeded
|
||||
&& page_id_cur != page_id_prv) { // and page_id is diff; keeps all page_ids in one db
|
||||
cat_link_tbl = Make_cat_link_tbl(wiki, cat_link_tbl);
|
||||
@@ -56,7 +58,7 @@ class Xob_catlink_wkr {
|
||||
page_id_prv = page_id_cur;
|
||||
|
||||
// insert; notify;
|
||||
cat_link_tbl.Insert_cmd_by_batch(page_id_prv, rdr.Read_int("page_id"), rdr.Read_byte("cl_type_id"), rdr.Read_int("cs_id"), rdr.Read_long("cl_timestamp"));
|
||||
cat_link_tbl.Insert_cmd_by_batch(page_id_prv, rdr.Read_int("page_id"), rdr.Read_byte("cl_type_id"), rdr.Read_long("cl_timestamp"), sortkey, sortkey_prefix);
|
||||
if (++rows % 100000 == 0)
|
||||
Gfo_usr_dlg_.Instance.Prog_many("", "", "inserting cat_link row: ~{0}", Int_.To_str_fmt(rows, "#,##0"));
|
||||
}
|
||||
@@ -82,8 +84,8 @@ class Xob_catlink_wkr {
|
||||
private static void Term_cat_link_tbl(Xodb_cat_link_tbl cat_link_tbl) {
|
||||
if (cat_link_tbl == null) return;
|
||||
cat_link_tbl.Insert_end();
|
||||
cat_link_tbl.Create_idx__from();
|
||||
cat_link_tbl.Create_idx__to_id();
|
||||
cat_link_tbl.Create_idx__catbox();
|
||||
cat_link_tbl.Create_idx__catpage();
|
||||
}
|
||||
public void Make_catcore_tbl(Xowe_wiki wiki, Db_conn tmp_conn, Db_conn page_conn, Db_conn cat_core_conn) {
|
||||
Db_attach_mgr attach_mgr = new Db_attach_mgr(cat_core_conn, new Db_attach_itm("temp_db", tmp_conn), new Db_attach_itm("page_db", page_conn));
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,45 +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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.bldrs.ucas; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.bldrs.*;
|
||||
import org.junit.*; import gplx.xowa.bldrs.*;
|
||||
public class Uca_trie_tst {
|
||||
@Before public void init() {fxt.Clear();} private Xob_base_fxt fxt = new Xob_base_fxt();
|
||||
@Test public void Basic() {
|
||||
Uca_trie_fxt fxt = new Uca_trie_fxt();
|
||||
fxt.Clear();
|
||||
fxt.Init_trie_itm("a", Bry_.New_by_ints(10, 11));
|
||||
fxt.Init_trie_itm("b", Bry_.New_by_ints(20, 21));
|
||||
fxt.Init_trie_itm("c", Bry_.New_by_ints(30, 31));
|
||||
fxt.Test_decode(Bry_.New_by_ints(10, 11), "a");
|
||||
fxt.Test_decode(Bry_.New_by_ints(10, 11, 20, 21, 30, 31), "abc");
|
||||
}
|
||||
}
|
||||
class Uca_trie_fxt {
|
||||
public void Clear() {
|
||||
if (trie == null) {
|
||||
trie = new Uca_trie();
|
||||
bfr = Bry_bfr_.New();
|
||||
}
|
||||
trie.Clear();
|
||||
} Uca_trie trie; Bry_bfr bfr;
|
||||
public void Init_trie_itm(String charAsStr, byte[] uca) {trie.Init_itm(gplx.core.intls.Utf16_.Decode_to_int(Bry_.new_u8(charAsStr), 0), uca);}
|
||||
public void Test_decode(byte[] bry, String expd) {
|
||||
trie.Decode(bfr, bry, 0, bry.length);
|
||||
Tfds.Eq(expd, bfr.To_str_and_clear());
|
||||
}
|
||||
}
|
||||
@@ -20,32 +20,34 @@ import gplx.dbs.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.pageboxs.*;
|
||||
public class Xodb_cat_link_tbl implements Db_tbl {
|
||||
private final Dbmeta_fld_list flds = new Dbmeta_fld_list();
|
||||
private final String fld_from, fld_to_id, fld_type_id, fld_sortkey_id, fld_timestamp_unix;
|
||||
private final String fld__from, fld__to_id, fld__type_id, fld__timestamp_unix, fld__sortkey, fld__sortkey_prefix;
|
||||
private Db_stmt stmt_insert;
|
||||
public Xodb_cat_link_tbl(Db_conn conn) {
|
||||
this.conn = conn;
|
||||
this.tbl_name = "cat_link";
|
||||
this.fld_from = flds.Add_int ("cl_from");
|
||||
this.fld_to_id = flds.Add_int ("cl_to_id");
|
||||
this.fld_type_id = flds.Add_byte ("cl_type_id");
|
||||
this.fld_sortkey_id = flds.Add_int ("cl_sortkey_id");
|
||||
this.fld_timestamp_unix = flds.Add_long ("cl_timestamp_unix");
|
||||
this.fld__from = flds.Add_int ("cl_from");
|
||||
this.fld__to_id = flds.Add_int ("cl_to_id");
|
||||
this.fld__type_id = flds.Add_byte ("cl_type_id");
|
||||
this.fld__timestamp_unix = flds.Add_long ("cl_timestamp_unix");
|
||||
this.fld__sortkey = flds.Add_bry ("cl_sortkey");
|
||||
this.fld__sortkey_prefix = flds.Add_str ("cl_sortkey_prefix", 255);
|
||||
conn.Rls_reg(this);
|
||||
}
|
||||
public Db_conn Conn() {return conn;} private final Db_conn conn;
|
||||
public String Tbl_name() {return tbl_name;} private final String tbl_name;
|
||||
public void Create_tbl() {conn.Meta_tbl_create(Dbmeta_tbl_itm.New(tbl_name, flds));}
|
||||
public void Create_idx__from() {conn.Meta_idx_create(Dbmeta_idx_itm.new_normal_by_tbl(tbl_name, fld_from, fld_from));}
|
||||
public void Create_idx__to_id() {conn.Meta_idx_create(Dbmeta_idx_itm.new_normal_by_tbl(tbl_name, fld_to_id, fld_to_id));}
|
||||
public void Create_idx__catbox() {conn.Meta_idx_create(Dbmeta_idx_itm.new_normal_by_tbl(tbl_name, "catbox", fld__from));}
|
||||
public void Create_idx__catpage() {conn.Meta_idx_create(Dbmeta_idx_itm.new_normal_by_tbl(tbl_name, "catpage", fld__to_id, fld__type_id, fld__sortkey));}
|
||||
public void Insert_bgn() {conn.Txn_bgn("cl__insert"); stmt_insert = conn.Stmt_insert(tbl_name, flds);}
|
||||
public void Insert_end() {conn.Txn_end(); stmt_insert = Db_stmt_.Rls(stmt_insert);}
|
||||
public void Insert_cmd_by_batch(int from, int to_id, byte type_id, int sortkey_id, long timestamp_unix) {
|
||||
public void Insert_cmd_by_batch(int from, int to_id, byte type_id, long timestamp_unix, byte[] sortkey, byte[] sortkey_prefix) {
|
||||
stmt_insert.Clear()
|
||||
.Val_int(fld_from , from)
|
||||
.Val_int(fld_to_id , to_id)
|
||||
.Val_byte(fld_type_id , type_id)
|
||||
.Val_int(fld_sortkey_id , sortkey_id)
|
||||
.Val_long(fld_timestamp_unix , timestamp_unix)
|
||||
.Val_int(fld__from , from)
|
||||
.Val_int(fld__to_id , to_id)
|
||||
.Val_byte(fld__type_id , type_id)
|
||||
.Val_long(fld__timestamp_unix , timestamp_unix)
|
||||
.Val_bry(fld__sortkey , sortkey)
|
||||
.Val_bry_as_str(fld__sortkey_prefix , sortkey_prefix)
|
||||
.Exec_insert();
|
||||
}
|
||||
public void Rls() {
|
||||
|
||||
@@ -26,7 +26,7 @@ public class Xodb_tmp_cat_link_tbl implements Db_tbl {
|
||||
this.tbl_name = "tmp_cat_link";
|
||||
this.fld_from = flds.Add_int ("cl_from");
|
||||
this.fld_to_ttl = flds.Add_str ("cl_to_ttl", 255);
|
||||
this.fld_sortkey = flds.Add_str ("cl_sortkey", 230);
|
||||
this.fld_sortkey = flds.Add_bry ("cl_sortkey");
|
||||
this.fld_timestamp = flds.Add_long ("cl_timestamp");
|
||||
this.fld_sortkey_prefix = flds.Add_str ("cl_sortkey_prefix", 230);
|
||||
this.fld_collation_id = flds.Add_byte ("cl_collation_id");
|
||||
@@ -43,7 +43,7 @@ public class Xodb_tmp_cat_link_tbl implements Db_tbl {
|
||||
stmt_insert.Clear()
|
||||
.Val_int(fld_from , page_id)
|
||||
.Val_bry_as_str(fld_to_ttl , ctg_ttl)
|
||||
.Val_bry_as_str(fld_sortkey , sortkey)
|
||||
.Val_bry(fld_sortkey , sortkey)
|
||||
.Val_long(fld_timestamp , timestamp)
|
||||
.Val_bry_as_str(fld_sortkey_prefix , sortkey_prefix)
|
||||
.Val_byte(fld_collation_id , collation_id)
|
||||
|
||||
@@ -17,14 +17,21 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*;
|
||||
import gplx.xowa.wikis.dbs.*; import gplx.xowa.wikis.data.tbls.*;
|
||||
import gplx.xowa.langs.*; import gplx.xowa.langs.msgs.*; import gplx.xowa.htmls.core.htmls.*;
|
||||
import gplx.xowa.langs.*; import gplx.xowa.langs.msgs.*; import gplx.xowa.htmls.core.htmls.*; import gplx.core.intls.ucas.*;
|
||||
import gplx.xowa.wikis.nss.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.fmts.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.utls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.urls.*;
|
||||
public class Xoctg_catpage_mgr {
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.fmts.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.dbs.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.urls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.langs.*;
|
||||
public class Xoctg_catpage_mgr implements Gfo_invk {
|
||||
private final Xow_wiki wiki;
|
||||
private final Hash_adp_bry cache = Hash_adp_bry.cs();
|
||||
private final Xoctg_catpage_loader loader = new Xoctg_catpage_loader();
|
||||
private final Xoctg_fmt_grp fmt_subcs = Xoctg_fmt_grp.New__subc(), fmt_pages = Xoctg_fmt_grp.New__page(), fmt_files = Xoctg_fmt_grp.New__file();
|
||||
private final Uca_ltr_extractor ltr_extractor = new Uca_ltr_extractor(true);
|
||||
public int Grp_max() {return grp_max;} private int grp_max = Grp_max_dflt;
|
||||
public Xoctg_catpage_mgr(Xow_wiki wiki) {
|
||||
this.wiki = wiki;
|
||||
this.collation_mgr = new Xoctg_collation_mgr(wiki);
|
||||
}
|
||||
public Xoctg_collation_mgr Collation_mgr() {return collation_mgr;} private Xoctg_collation_mgr collation_mgr;
|
||||
public Xoctg_fmt_grp Fmt(byte tid) {
|
||||
switch (tid) {
|
||||
case Xoa_ctg_mgr.Tid__subc: return fmt_subcs;
|
||||
@@ -34,32 +41,33 @@ public class Xoctg_catpage_mgr {
|
||||
}
|
||||
}
|
||||
public void Free_mem_all() {cache.Clear();}
|
||||
public Xoctg_catpage_ctg Get_or_load_or_null(Xow_wiki wiki, Xoa_ttl cat_ttl) {
|
||||
public Xoctg_catpage_ctg Get_or_load_or_null(Xoctg_catpage_url catpage_url, Xoa_ttl cat_ttl, int limit) {
|
||||
// load categories from cat dbs; exit if not found
|
||||
Xoctg_catpage_ctg ctg = (Xoctg_catpage_ctg)cache.Get_by(cat_ttl.Full_db());
|
||||
if (ctg == null) {
|
||||
if (gplx.core.envs.Env_.Mode_testing()) return null; // needed for dpl test
|
||||
ctg = loader.Load_by_ttl_or_null(wiki, cat_ttl);
|
||||
synchronized (thread_lock) { // LOCK:used by multiple wrks; DATE:2016-09-12
|
||||
ctg = loader.Load_ctg_or_null(wiki, this, catpage_url, cat_ttl, limit);
|
||||
}
|
||||
if (ctg == null) return null; // not in cache or db; exit
|
||||
cache.Add(cat_ttl.Full_db(), ctg);
|
||||
// cache.Add(cat_ttl.Full_db(), ctg);
|
||||
}
|
||||
return ctg;
|
||||
}
|
||||
public void Write_catpage(Bry_bfr bfr, Xow_wiki wiki, Xoa_page page, Xoh_wtr_ctx hctx) {
|
||||
public void Write_catpage(Bry_bfr bfr, Xoa_page page, Xoh_wtr_ctx hctx) {
|
||||
try {
|
||||
// load categories from cat dbs; exit if not found
|
||||
Xoctg_catpage_ctg ctg = Get_or_load_or_null(wiki, page.Ttl());
|
||||
if (ctg == null) return;
|
||||
|
||||
// filter subs; need for large categories like de.w:Category:Mann
|
||||
// get catpage_url
|
||||
Xoctg_catpage_url catpage_url = Xoctg_catpage_url_parser.Parse(page.Url());
|
||||
Xoctg_catpage_filter.Filter(grp_max, catpage_url, ctg);
|
||||
|
||||
// load categories from cat dbs; exit if not found
|
||||
Xoctg_catpage_ctg ctg = Get_or_load_or_null(catpage_url, page.Ttl(), grp_max);
|
||||
if (ctg == null) return;
|
||||
|
||||
// write html
|
||||
Xol_lang_itm lang = page.Lang();
|
||||
fmt_subcs.Write_catpage_grp(bfr, wiki, lang, ctg, grp_max);
|
||||
fmt_pages.Write_catpage_grp(bfr, wiki, lang, ctg, grp_max);
|
||||
fmt_files.Write_catpage_grp(bfr, wiki, lang, ctg, grp_max);
|
||||
fmt_subcs.Write_catpage_grp(bfr, wiki, lang, ltr_extractor, ctg, grp_max);
|
||||
fmt_pages.Write_catpage_grp(bfr, wiki, lang, ltr_extractor, ctg, grp_max);
|
||||
fmt_files.Write_catpage_grp(bfr, wiki, lang, ltr_extractor, ctg, grp_max);
|
||||
}
|
||||
catch (Exception e) {
|
||||
Xoa_app_.Usr_dlg().Warn_many("", "", "failed to generate category: title=~{0} err=~{1}", page.Url_bry_safe(), Err_.Message_gplx_log(e));
|
||||
@@ -70,5 +78,12 @@ public class Xoctg_catpage_mgr {
|
||||
cache.Add(ttl, ctg);
|
||||
}
|
||||
public void Grp_max_(int v) {grp_max = v;} // TEST:
|
||||
public Object Invk(GfsCtx ctx, int ikey, String k, GfoMsg m) {
|
||||
if (ctx.Match(k, Invk__collation_)) collation_mgr.Collation_name_(m.ReadStr("v"));
|
||||
else return Gfo_invk_.Rv_unhandled;
|
||||
return this;
|
||||
} private static final String Invk__collation_ = "collation_";
|
||||
|
||||
public static int Grp_max_dflt = 200;
|
||||
private static final Object thread_lock = new Object();
|
||||
}
|
||||
|
||||
@@ -16,25 +16,27 @@ You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*;
|
||||
import org.junit.*; import gplx.xowa.htmls.core.htmls.*;
|
||||
import org.junit.*; import gplx.xowa.htmls.core.htmls.*; import gplx.core.intls.ucas.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.fmts.*;
|
||||
public class Xoctg_catpage_mgr__basic__tst {
|
||||
@Before public void init() {fxt.Clear();} private Xoctg_catpage_mgr_fxt fxt = new Xoctg_catpage_mgr_fxt();
|
||||
@Test public void Page_itm() {
|
||||
fxt .Init_itms__pages("A1")
|
||||
.Test__html__page(Xoa_ctg_mgr.Tid__page, Byte_ascii.Ltr_A, "\n <li><a href=\"/wiki/A1\" title=\"A1\">A1</a></li>");
|
||||
.Test__html__page(Xoa_ctg_mgr.Tid__page, Byte_ascii.Ltr_A, "\n <li><a href=\"/wiki/A1\" title=\"A1\">A1</a><!----></li>");
|
||||
}
|
||||
@Test public void Page_itm_missing() {
|
||||
fxt .Init_itms__pages("A1");
|
||||
fxt .Ctg().Grp_by_tid(Xoa_ctg_mgr.Tid__page).Itms__get_at(0).Missing_y_();
|
||||
fxt .Test__html__page(Xoa_ctg_mgr.Tid__page, Byte_ascii.Ltr_A, "\n <li class=\"xowa-missing-category-entry\"><span title=\"id not found: #0 might be talk/user page\">A1 (missing)</li>");
|
||||
fxt.Init_itms__pages("A1");
|
||||
Xoctg_catpage_itm itm = fxt.Ctg().Grp_by_tid(Xoa_ctg_mgr.Tid__page).Itms__get_at(0);
|
||||
itm.Page_ttl_(Xoa_ttl.Null);
|
||||
itm.Sortkey_handle_make(Bry_bfr_.New(), Bry_.Empty);
|
||||
fxt.Test__html__page(Xoa_ctg_mgr.Tid__page, Byte_ascii.Ltr_A, "\n <li class=\"xowa-missing-category-entry\"><span title=\"id not found: #0 might be talk/user page\">A1 (missing)</li>");
|
||||
}
|
||||
@Test public void Visited_doesnt_work_for_space() {// PURPOSE: xowa-visited not inserted for pages with space
|
||||
byte[] page_bry = Bry_.new_a7("A 1");
|
||||
Xoa_url url = Xoa_url.New(Bry_.new_a7("en.wikipedia.org"), page_bry);
|
||||
Xoa_ttl ttl = Xoa_ttl.Parse(fxt.Wiki(), page_bry);
|
||||
fxt.Wiki().Appe().Usere().History_mgr().Add(url, ttl, page_bry);
|
||||
fxt .Init_itms__pages("A_1").Init_grp__pages(0, 1)
|
||||
fxt .Init_itms__pages("A_1")
|
||||
.Test__html__all(Xoa_ctg_mgr.Tid__page, String_.Concat_lines_nl_skip_last
|
||||
( ""
|
||||
, "<div id=\"mw-pages\">"
|
||||
@@ -46,7 +48,7 @@ public class Xoctg_catpage_mgr__basic__tst {
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>A</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/A_1\" class=\"xowa-visited\" title=\"A 1\">A 1</a></li>"
|
||||
, " <li><a href=\"/wiki/A_1\" class=\"xowa-visited\" title=\"A 1\">A 1</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " </tr>"
|
||||
@@ -56,7 +58,7 @@ public class Xoctg_catpage_mgr__basic__tst {
|
||||
));
|
||||
}
|
||||
@Test public void Page_all() {
|
||||
fxt .Init_itms__pages("A1").Init_grp__pages(0, 1)
|
||||
fxt .Init_itms__pages("A1")
|
||||
.Test__html__all(Xoa_ctg_mgr.Tid__page, String_.Concat_lines_nl_skip_last
|
||||
( ""
|
||||
, "<div id=\"mw-pages\">"
|
||||
@@ -68,7 +70,7 @@ public class Xoctg_catpage_mgr__basic__tst {
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>A</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/A1\" title=\"A1\">A1</a></li>"
|
||||
, " <li><a href=\"/wiki/A1\" title=\"A1\">A1</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " </tr>"
|
||||
@@ -78,7 +80,7 @@ public class Xoctg_catpage_mgr__basic__tst {
|
||||
));
|
||||
}
|
||||
@Test public void File_all() {
|
||||
fxt .Init_itms__files("File:A1.png").Init_grp__files(0, 1)
|
||||
fxt .Init_itms__files("File:A1.png")
|
||||
.Test__html__all(Xoa_ctg_mgr.Tid__file, String_.Concat_lines_nl_skip_last
|
||||
( ""
|
||||
, "<div id=\"mw-category-media\">"
|
||||
@@ -90,7 +92,7 @@ public class Xoctg_catpage_mgr__basic__tst {
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>A</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/File:A1.png\" title=\"File:A1.png\">File:A1.png</a></li>"
|
||||
, " <li><a href=\"/wiki/File:A1.png\" title=\"File:A1.png\">File:A1.png</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " </tr>"
|
||||
@@ -98,25 +100,9 @@ public class Xoctg_catpage_mgr__basic__tst {
|
||||
, " </div>"
|
||||
, "</div>"
|
||||
));
|
||||
// , " <ul id=\"xowa_gallery_ul_0\" class=\"gallery\">"
|
||||
// , " <li class=\"gallerybox\" style=\"width:155px;\">"
|
||||
// , " <div style=\"width:155px;\">"
|
||||
// , " <div class=\"thumb\" style=\"width:155px;\">"
|
||||
// , " <div id=\"xowa_gallery_div3_-1\" style=\"margin:15px auto;\">"
|
||||
// , " <a href=\"/wiki/File:A1.png\" class=\"image\">"
|
||||
// , " <img id=\"xoimg_-1\" alt=\"A1.png\" src=\"\" width=\"-1\" height=\"-1\" />"
|
||||
// , " </a>"
|
||||
// , " </div>"
|
||||
// , " </div>"
|
||||
// , " <div class=\"gallerytext\">A1.png"
|
||||
// , " </div>"
|
||||
// , " </div>"
|
||||
// , " </li>"
|
||||
// , ""
|
||||
// , " </ul>"
|
||||
}
|
||||
@Test public void Subc_all() {
|
||||
fxt .Init_itms__subcs("Category:Subc_1").Init_grp__files(0, 1)
|
||||
fxt .Init_itms__subcs("Category:Subc_1")
|
||||
.Test__html__all(Xoa_ctg_mgr.Tid__subc, String_.Concat_lines_nl_skip_last
|
||||
( ""
|
||||
, "<div id=\"mw-subcategories\">"
|
||||
@@ -152,46 +138,82 @@ public class Xoctg_catpage_mgr__basic__tst {
|
||||
));
|
||||
}
|
||||
@Test public void Page_all_cols() {
|
||||
fxt .Init_itms__pages("A1", "A2", "A3", "B1", "C1").Init_grp__pages(0, 5)
|
||||
.Test__html__all(Xoa_ctg_mgr.Tid__page, String_.Concat_lines_nl_skip_last
|
||||
( ""
|
||||
, "<div id=\"mw-pages\">"
|
||||
, " <h2>Pages in category \"Ctg_1\"</h2>"
|
||||
, " <p>The following 5 pages are in this category, out of 5 total.</p>"
|
||||
, " <div lang=\"en\" dir=\"ltr\" class=\"mw-content-ltr\">"
|
||||
, " <table style=\"width: 100%;\">"
|
||||
, " <tr style=\"vertical-align: top;\">"
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>A</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/A1\" title=\"A1\">A1</a></li>"
|
||||
, " <li><a href=\"/wiki/A2\" title=\"A2\">A2</a></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>A cont.</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/A3\" title=\"A3\">A3</a></li>"
|
||||
, " </ul>"
|
||||
, " <h3>B</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/B1\" title=\"B1\">B1</a></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>C</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/C1\" title=\"C1\">C1</a></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " </tr>"
|
||||
, " </table>"
|
||||
, " </div>"
|
||||
, "</div>"
|
||||
));
|
||||
fxt.Init_itms__pages("A1", "A2", "A3", "B1", "C1");
|
||||
fxt.Init__grp_max_(6);
|
||||
fxt.Test__html__all(Xoa_ctg_mgr.Tid__page, String_.Concat_lines_nl_skip_last
|
||||
( ""
|
||||
, "<div id=\"mw-pages\">"
|
||||
, " <h2>Pages in category \"Ctg_1\"</h2>"
|
||||
, " <p>The following 5 pages are in this category, out of 5 total.</p>"
|
||||
, " <div lang=\"en\" dir=\"ltr\" class=\"mw-content-ltr\">"
|
||||
, " <table style=\"width: 100%;\">"
|
||||
, " <tr style=\"vertical-align: top;\">"
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>A</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/A1\" title=\"A1\">A1</a><!----></li>"
|
||||
, " <li><a href=\"/wiki/A2\" title=\"A2\">A2</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>A cont.</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/A3\" title=\"A3\">A3</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " <h3>B</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/B1\" title=\"B1\">B1</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>C</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/C1\" title=\"C1\">C1</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " </tr>"
|
||||
, " </table>"
|
||||
, " </div>"
|
||||
, "</div>"
|
||||
));
|
||||
}
|
||||
@Test public void Page__numeric() { // PURPOSE: check numeric sorting; 0, 9, 10; not 0, 10, 9; DATE:2016-10-09
|
||||
fxt.Init_itms__pages("0", "9", "10");
|
||||
fxt.Init__grp_max_(6);
|
||||
fxt.Test__html__all(Xoa_ctg_mgr.Tid__page, String_.Concat_lines_nl_skip_last
|
||||
( ""
|
||||
, "<div id=\"mw-pages\">"
|
||||
, " <h2>Pages in category \"Ctg_1\"</h2>"
|
||||
, " <p>The following 3 pages are in this category, out of 3 total.</p>"
|
||||
, " <div lang=\"en\" dir=\"ltr\" class=\"mw-content-ltr\">"
|
||||
, " <table style=\"width: 100%;\">"
|
||||
, " <tr style=\"vertical-align: top;\">"
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>0-9</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/0\" title=\"0\">0</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>0-9 cont.</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/9\" title=\"9\">9</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>0-9 cont.</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/10\" title=\"10\">10</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " </tr>"
|
||||
, " </table>"
|
||||
, " </div>"
|
||||
, "</div>"
|
||||
));
|
||||
}
|
||||
@Test public void Title__escape_quotes() {// PURPOSE: quotes in title should be escaped; DATE:2015-12-28
|
||||
fxt .Init_itms__pages("A\"1").Init_grp__pages(0, 1)
|
||||
fxt .Init_itms__pages("A\"1")
|
||||
.Test__html__all(Xoa_ctg_mgr.Tid__page, String_.Concat_lines_nl_skip_last
|
||||
( ""
|
||||
, "<div id=\"mw-pages\">"
|
||||
@@ -203,7 +225,7 @@ public class Xoctg_catpage_mgr__basic__tst {
|
||||
, " <td style=\"width: 33%;\">"
|
||||
, " <h3>A</h3>"
|
||||
, " <ul>"
|
||||
, " <li><a href=\"/wiki/A%221\" title=\"A"1\">A"1</a></li>"
|
||||
, " <li><a href=\"/wiki/A%221\" title=\"A"1\">A"1</a><!----></li>"
|
||||
, " </ul>"
|
||||
, " </td>"
|
||||
, " </tr>"
|
||||
@@ -226,44 +248,49 @@ public class Xoctg_catpage_mgr__basic__tst {
|
||||
}
|
||||
class Xoctg_catpage_mgr_fxt {
|
||||
private int grp_max;
|
||||
private Uca_ltr_extractor ltr_extractor = new Uca_ltr_extractor(true);
|
||||
public Xoctg_catpage_mgr_fxt Clear() {
|
||||
if (app == null) {
|
||||
app = Xoa_app_fxt.Make__app__edit();
|
||||
wiki = Xoa_app_fxt.Make__wiki__edit(app);
|
||||
ctg_html = wiki.Html_mgr().Catpage_mgr();
|
||||
ctg_html = wiki.Ctg__catpage_mgr();
|
||||
}
|
||||
ctg = new Xoctg_catpage_ctg(Bry_.new_a7("Ctg_1"));
|
||||
grp_max = Xoctg_catpage_mgr.Grp_max_dflt;
|
||||
ctg = new Xoctg_catpage_ctg(1, Bry_.new_a7("Ctg_1"));
|
||||
grp_max = 3; // default to 3 paer page
|
||||
return this;
|
||||
} private Xoae_app app; private Xoctg_catpage_mgr ctg_html;
|
||||
public void Test__calc_col_len(int grp_len, int col_idx, int expd) {Tfds.Eq(expd, Xoctg_fmt_itm_base.Calc_col_len(grp_len, col_idx, 3));}
|
||||
public Xowe_wiki Wiki() {return wiki;} private Xowe_wiki wiki;
|
||||
public Xoctg_catpage_ctg Ctg() {return ctg;} private Xoctg_catpage_ctg ctg;
|
||||
public void Init__grp_max_(int v) {this.grp_max = v;}
|
||||
public void Init__prev_hide_y_(byte tid) {ctg.Grp_by_tid(tid).Prev_disable_(true);}
|
||||
public void Init__next_sortkey_(byte tid, String v) {ctg.Grp_by_tid(tid).Next_sortkey_(Bry_.new_u8(v));}
|
||||
public void Test__navlink(boolean next, String ctg_str, String expd) {
|
||||
byte[] actl = ctg_html.Fmt(Xoa_ctg_mgr.Tid__page).Bld_bwd_fwd(wiki, Xoa_ttl.Parse(wiki, Bry_.new_a7(ctg_str)), ctg.Grp_by_tid(Xoa_ctg_mgr.Tid__page), grp_max);
|
||||
Tfds.Eq_str_lines(expd, String_.new_u8(actl));
|
||||
}
|
||||
public Xoctg_catpage_mgr_fxt Init_grp_max(int v) {this.grp_max = v; return this;}
|
||||
public Xoctg_catpage_mgr_fxt Init_grp__pages(int bgn, int count) {ctg.Pages().Rng_(bgn, count); return this;}
|
||||
public Xoctg_catpage_mgr_fxt Init_grp__files(int bgn, int count) {ctg.Files().Rng_(bgn, count); return this;}
|
||||
public Xoctg_catpage_mgr_fxt Init_itms__pages(String... titles) {return Init_itms(Xoa_ctg_mgr.Tid__page, titles);}
|
||||
public Xoctg_catpage_mgr_fxt Init_itms__files(String... titles) {return Init_itms(Xoa_ctg_mgr.Tid__file, titles);}
|
||||
public Xoctg_catpage_mgr_fxt Init_itms__subcs(String... titles) {return Init_itms(Xoa_ctg_mgr.Tid__subc, titles);}
|
||||
private Xoctg_catpage_mgr_fxt Init_itms(byte tid, String[] ttls) {
|
||||
int len = ttls.length;
|
||||
Xoctg_catpage_tmp tmp = new Xoctg_catpage_tmp();
|
||||
Xoctg_catpage_grp grp = ctg.Grp_by_tid(tid);
|
||||
grp.Count_all_(len);
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Xoa_ttl ttl = Xoa_ttl.Parse(wiki, Bry_.new_u8(ttls[i]));
|
||||
grp.Itms__add(new Xoctg_catpage_itm(i, ttl, ttl.Page_txt()));
|
||||
byte[] page_ttl_bry = Bry_.new_u8(ttls[i]);
|
||||
Xoa_ttl ttl = Xoa_ttl.Parse(wiki, page_ttl_bry);
|
||||
Xoctg_catpage_itm itm = Xoctg_catpage_itm.New_by_ttl(tid, i, ttl);
|
||||
tmp.Add(itm);
|
||||
}
|
||||
grp.Itms__make();
|
||||
tmp.Make_by_grp(grp);
|
||||
return this;
|
||||
}
|
||||
public void Test__html__page(byte tid, byte grp_char_0, String expd) {
|
||||
Xoctg_fmt_grp list_mgr = ctg_html.Fmt(tid);
|
||||
Xoctg_fmt_itm_base itm_fmt = list_mgr.Itm_fmt();
|
||||
Xoctg_catpage_grp list = ctg.Grp_by_tid(tid);
|
||||
itm_fmt.Init_from_ltr(wiki, list);
|
||||
itm_fmt.Init_from_ltr(wiki, list, ltr_extractor);
|
||||
itm_fmt.Set_ltr_and_bgn(new byte[] {grp_char_0}, 0);
|
||||
itm_fmt.Col_end_(0, 0);
|
||||
Bry_bfr bfr = wiki.Utl__bfr_mkr().Get_b512();
|
||||
@@ -273,14 +300,14 @@ class Xoctg_catpage_mgr_fxt {
|
||||
public void Test__html_grp(byte tid, String expd) {
|
||||
Xoctg_fmt_grp list_mgr = ctg_html.Fmt(tid);
|
||||
Xoctg_fmt_ltr fmtr_grp = new Xoctg_fmt_ltr(list_mgr.Itm_fmt());
|
||||
fmtr_grp.Init_from_grp(wiki, ctg.Grp_by_tid(tid));
|
||||
fmtr_grp.Init_from_grp(wiki, ctg.Grp_by_tid(tid), ltr_extractor);
|
||||
Bry_bfr bfr = wiki.Utl__bfr_mkr().Get_b512();
|
||||
fmtr_grp.Bfr_arg__add(bfr);
|
||||
Tfds.Eq_str_lines(expd, bfr.To_str_and_rls());
|
||||
}
|
||||
public void Test__html__all(byte tid, String expd) {
|
||||
Bry_bfr bfr = wiki.Utl__bfr_mkr().Get_b512();
|
||||
ctg_html.Fmt(tid).Write_catpage_grp(bfr, wiki, wiki.Lang(), ctg, grp_max);
|
||||
ctg_html.Fmt(tid).Write_catpage_grp(bfr, wiki, wiki.Lang(), ltr_extractor, ctg, grp_max);
|
||||
Tfds.Eq_str_lines(expd, bfr.To_str_and_rls());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -21,43 +21,39 @@ import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*; import gplx.xowa.addon
|
||||
public class Xoctg_catpage_mgr__navlink__tst {
|
||||
@Before public void init() {fxt.Clear();} private Xoctg_catpage_mgr_fxt fxt = new Xoctg_catpage_mgr_fxt();
|
||||
@Test public void Navlink__basic() {
|
||||
fxt .Init_itms__pages("A1", "A2", "A3").Init_grp_max(1).Init_grp__pages(1, 2)
|
||||
.Test__navlink(Bool_.Y, "Category:Ctg_1", String_.Concat_lines_nl
|
||||
fxt.Init_itms__pages("A2", "A3", "A4");
|
||||
fxt.Init__next_sortkey_(Xoa_ctg_mgr.Tid__page, "A5");
|
||||
fxt.Test__navlink(Bool_.Y, "Category:Ctg_1", String_.Concat_lines_nl
|
||||
( ""
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pageuntil=A2#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">previous 1</a>)"
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pagefrom=A3#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">next 1</a>)"
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pageuntil=A2%0AA2#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">previous 3</a>)"
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pagefrom=A5#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">next 3</a>)"
|
||||
));
|
||||
}
|
||||
@Test public void Navlink__encoded() { // escape quotes and spaces; DATE:2016-01-11
|
||||
fxt .Init_itms__pages("A\" 1", "A\" 2", "A\" 3").Init_grp_max(1).Init_grp__pages(1, 2)
|
||||
.Test__navlink(Bool_.Y, "Category:Ctg_1", String_.Concat_lines_nl
|
||||
fxt.Init_itms__pages("A\" 2", "A\" 3", "A\" 4");
|
||||
fxt.Init__next_sortkey_(Xoa_ctg_mgr.Tid__page, "A\" 5");
|
||||
fxt.Test__navlink(Bool_.Y, "Category:Ctg_1", String_.Concat_lines_nl
|
||||
( ""
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pageuntil=A%22+2#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">previous 1</a>)"
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pagefrom=A%22+3#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">next 1</a>)"
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pageuntil=A%22+2%0AA%22+2#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">previous 3</a>)"
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pagefrom=A%22+5#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">next 3</a>)"
|
||||
));
|
||||
}
|
||||
@Test public void Navlink__bos() {
|
||||
fxt .Init_itms__pages("A1", "A2", "A3").Init_grp_max(1).Init_grp__pages(0, 1)
|
||||
.Test__navlink(Bool_.Y, "Category:Ctg_1", String_.Concat_lines_nl
|
||||
fxt.Init_itms__pages("A2", "A3", "A4");
|
||||
fxt.Init__prev_hide_y_(Xoa_ctg_mgr.Tid__page);
|
||||
fxt.Init__next_sortkey_(Xoa_ctg_mgr.Tid__page, "A5");
|
||||
fxt.Test__navlink(Bool_.Y, "Category:Ctg_1", String_.Concat_lines_nl
|
||||
( ""
|
||||
, "(previous 1)"
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pagefrom=A2#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">next 1</a>)"
|
||||
, "(previous 3)"
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pagefrom=A5#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">next 3</a>)"
|
||||
));
|
||||
}
|
||||
@Test public void Navlink__eos() {
|
||||
fxt .Init_itms__pages("A1", "A2", "A3").Init_grp_max(2).Init_grp__pages(2, 3)
|
||||
.Test__navlink(Bool_.Y, "Category:Ctg_1", String_.Concat_lines_nl
|
||||
fxt.Init_itms__pages("A2", "A3", "A4");
|
||||
fxt.Test__navlink(Bool_.Y, "Category:Ctg_1", String_.Concat_lines_nl
|
||||
( ""
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pageuntil=A3#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">previous 2</a>)"
|
||||
, "(next 2)"
|
||||
));
|
||||
}
|
||||
@Test public void Navlink__eos__2() { // PURPOSE.fix: do not suppress next page on penultimate page; DATE:2016-09-25
|
||||
fxt .Init_itms__pages("A1", "A2", "A3", "A4").Init_grp_max(2).Init_grp__pages(2, 3)
|
||||
.Test__navlink(Bool_.Y, "Category:Ctg_1", String_.Concat_lines_nl
|
||||
( ""
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pageuntil=A3#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">previous 2</a>)"
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pagefrom=A4#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">next 2</a>)"
|
||||
, "(<a href=\"/wiki/Category:Ctg_1?pageuntil=A2%0AA2#mw-pages\" class=\"xowa_nav\" title=\"Category:Ctg_1\">previous 3</a>)"
|
||||
, "(next 3)"
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,182 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.dbs.*; import gplx.xowa.wikis.data.*; import gplx.xowa.wikis.data.tbls.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.langs.*;
|
||||
class Xoctg_catlink_loader {
|
||||
private byte version;
|
||||
private int link_dbs_len;
|
||||
private Db_attach_mgr attach_mgr;
|
||||
private final Bry_bfr sortkey_val_bfr = Bry_bfr_.New();
|
||||
public void Run(Xoctg_catpage_ctg rv, Xow_wiki wiki, Xoctg_catpage_mgr catpage_mgr, Xowd_page_tbl page_tbl, int cat_id, byte grp_tid, boolean url_is_from, byte[] url_sortkey, int limit) {
|
||||
String sql = Bld_sql(catpage_mgr, cat_id, grp_tid, url_is_from, url_sortkey, limit);
|
||||
Load_catlinks(rv, wiki, page_tbl, rv.Grp_by_tid(grp_tid), sql, url_is_from, limit);
|
||||
}
|
||||
public void Make_attach_mgr__v2(Xow_db_mgr db_mgr, int cat_link_db_idx) {
|
||||
this.version = 2;
|
||||
this.link_dbs_len = 1;
|
||||
Xow_db_file cat_link_db = db_mgr.Dbs__get_by_id_or_fail(cat_link_db_idx);
|
||||
this.attach_mgr = new Db_attach_mgr(cat_link_db.Conn(), new Db_attach_itm("link_db_1", cat_link_db.Conn()));
|
||||
}
|
||||
public void Make_attach_mgr__v3_v4(Xow_db_mgr db_mgr, Db_conn cat_core_conn) {
|
||||
// init db vars
|
||||
List_adp db_list = List_adp_.New();
|
||||
Db_conn db_1st = null;
|
||||
int db_idx = 0;
|
||||
|
||||
// fill db_list by looping over each db unless (a) cat_link_db or (b) core_db (if all or few)
|
||||
int len = db_mgr.Dbs__len();
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Xow_db_file cl_db = db_mgr.Dbs__get_at(i);
|
||||
switch (cl_db.Tid()) {
|
||||
case Xow_db_file_.Tid__cat_link: // always use cat_link db
|
||||
break;
|
||||
case Xow_db_file_.Tid__core: // only use core if all or few
|
||||
if (db_mgr.Props().Layout_text().Tid_is_lot())
|
||||
continue;
|
||||
else
|
||||
break;
|
||||
default: // skip all other files
|
||||
continue;
|
||||
}
|
||||
|
||||
// add to db_list
|
||||
if (db_1st == null) db_1st = cl_db.Conn();
|
||||
db_list.Add(new Db_attach_itm("link_db_" + ++db_idx, cl_db.Conn()));
|
||||
}
|
||||
|
||||
// make attach_mgr
|
||||
this.version = 4;
|
||||
this.link_dbs_len = db_list.Len();
|
||||
if (cat_core_conn.Meta_tbl_exists("cat_sort")) {
|
||||
version = 3;
|
||||
db_1st = cat_core_conn;
|
||||
}
|
||||
this.attach_mgr = new Db_attach_mgr(db_1st, (Db_attach_itm[])db_list.To_ary_and_clear(Db_attach_itm.class));
|
||||
}
|
||||
private String Bld_sql (Xoctg_catpage_mgr catpage_mgr, int cat_id, byte grp_tid, boolean url_is_from, byte[] url_sortkey, int limit) {
|
||||
Bry_bfr bfr = Bry_bfr_.New();
|
||||
for (int i = 0; i < link_dbs_len; ++i)
|
||||
Bld_sql_by_db(catpage_mgr, cat_id, grp_tid, url_is_from, url_sortkey, i + List_adp_.Base1, bfr);
|
||||
bfr.Add_str_u8_fmt
|
||||
( "\nORDER BY cl_to_id, cl_type_id, cl_sortkey {0}"
|
||||
+ "\nLIMIT {1}"
|
||||
, url_is_from ? "ASC" : "DESC", limit + 1);
|
||||
return bfr.To_str_and_clear();
|
||||
}
|
||||
private void Bld_sql_by_db (Xoctg_catpage_mgr catpage_mgr, int cat_id, byte grp_tid, boolean url_is_from, byte[] url_sortkey, int link_db_id, Bry_bfr bfr) {
|
||||
if (link_db_id != List_adp_.Base1) bfr.Add_str_a7("\nUNION\n");
|
||||
|
||||
// change sortkey vars per version; note that v3 differs from v2 and v4 b/c of cat_sort tbl
|
||||
String sortkey_col = "cl_sortkey";
|
||||
String sortkey_join = "";
|
||||
if (version == 3) { // NOTE: version 3 takes sortkey from cat_sort
|
||||
sortkey_col = "cs.cs_key";
|
||||
sortkey_join = "\n JOIN cat_sort cs ON cl.cl_sortkey_id = cs.cs_id";
|
||||
}
|
||||
|
||||
// sortkey_val
|
||||
byte[] sortkey_val = null;
|
||||
String sortkey_prefix_fld = version == 4 ? "cl_sortkey_prefix" : "''";
|
||||
sortkey_val = Build_sortkey_val(sortkey_val_bfr, version, catpage_mgr.Collation_mgr(), url_sortkey);
|
||||
|
||||
// bld sql; NOTE: building sql with args embedded b/c (a) UNION requires multiple Crt_arg for each ?; (EX: 4 unions, 3 ? require 12 .Crt_arg); (b) easier to debug
|
||||
String sql = Db_sql_.Make_by_fmt(String_.Ary
|
||||
( "SELECT cl_to_id"
|
||||
, ", cl_from"
|
||||
, ", cl_type_id"
|
||||
, ", {3} AS cl_sortkey"
|
||||
, ", {7} AS cl_sortkey_prefix"
|
||||
, "FROM <link_db_{0}>cat_link cl{6}"
|
||||
, "WHERE cl_to_id = {1}"
|
||||
, "AND cl_type_id = {2}"
|
||||
, "AND {3} {4} {5}"
|
||||
), link_db_id, cat_id, grp_tid, sortkey_col, url_is_from ? ">=" : "<", sortkey_val, sortkey_join, sortkey_prefix_fld);
|
||||
bfr.Add_str_u8(sql);
|
||||
}
|
||||
private void Load_catlinks(Xoctg_catpage_ctg rv, Xow_wiki wiki, Xowd_page_tbl page_tbl, Xoctg_catpage_grp grp, String sql, boolean url_is_from, int limit) {
|
||||
// init; prep sql
|
||||
Xoctg_page_loader catlink_loader = new Xoctg_page_loader(wiki);
|
||||
Ordered_hash hash = catlink_loader.Hash();
|
||||
sql = attach_mgr.Resolve_sql(sql);
|
||||
|
||||
// run sql and create itms based on cat_link
|
||||
Xoctg_catpage_itm itm_zth = null;
|
||||
Db_rdr rdr = Db_rdr_.Empty;
|
||||
int row_idx = 0;
|
||||
try {
|
||||
attach_mgr.Attach();
|
||||
rdr = attach_mgr.Conn_main().Stmt_sql(sql).Exec_select__rls_auto();
|
||||
while (rdr.Move_next()) {
|
||||
Xoctg_catpage_itm itm = Xoctg_catpage_itm.New_by_rdr(rdr, version);
|
||||
if (row_idx++ < limit) // row_idx >= limit for last row; EX: 200 < 200
|
||||
hash.Add(itm.Page_id(), itm);
|
||||
else { // last row; EX: 201
|
||||
if (url_is_from) // from=some_key; 201st row is sort_key for "(Next 200)"
|
||||
itm_zth = itm;
|
||||
else // until=some_key; 201st row means that 200th row is not 1st row; show prev link
|
||||
grp.Prev_disable_(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
finally {
|
||||
rdr.Rls();
|
||||
attach_mgr.Detach();
|
||||
}
|
||||
|
||||
// load ns / ttl from page
|
||||
page_tbl.Select_in__id(catlink_loader);
|
||||
grp.Itms_((Xoctg_catpage_itm[])hash.To_ary_and_clear(Xoctg_catpage_itm.class));
|
||||
|
||||
// set data for Next 200 / Previous 200
|
||||
if (itm_zth != null) {
|
||||
if (version == 4) {
|
||||
Xowd_page_itm tmp_pg = new Xowd_page_itm();
|
||||
page_tbl.Select_by_id(tmp_pg, itm_zth.Page_id());
|
||||
Xoa_ttl zth_ttl = wiki.Ttl_parse(tmp_pg.Ns_id(), tmp_pg.Ttl_page_db());
|
||||
itm_zth.Page_ttl_(zth_ttl);
|
||||
itm_zth.Sortkey_handle_make(Bry_bfr_.New(), grp.Itms__get_at(grp.Itms__len() - 1).Sortkey_handle());
|
||||
grp.Next_sortkey_(itm_zth.Sortkey_handle());
|
||||
}
|
||||
else
|
||||
grp.Next_sortkey_(itm_zth.Sortkey_handle());
|
||||
}
|
||||
}
|
||||
public static byte[] Build_sortkey_val(Bry_bfr sortkey_val_bfr, byte version, Xoctg_collation_mgr collation_mgr, byte[] url_sortkey) {
|
||||
// find \n and ignore everything after it; needed else "< 'A\nA'" will pull up "A"; NOTE: can't find logic in MediaWiki CategoryViewer.php; DATE:2016-10-11
|
||||
// ALSO: needed for v2 else SQL will literally have WHERE cl_sortkey = 'A\nA';
|
||||
byte[] tmp_sortkey = url_sortkey;
|
||||
int nl_pos = Bry_find_.Find_fwd(tmp_sortkey, Byte_ascii.Nl);
|
||||
if (nl_pos != Bry_find_.Not_found)
|
||||
tmp_sortkey = Bry_.Mid(tmp_sortkey, 0, nl_pos);
|
||||
|
||||
if (version == 4) {
|
||||
if (Bry_.Len_gt_0(url_sortkey)) {
|
||||
// make sortkey_val
|
||||
sortkey_val_bfr.Add_byte(Byte_ascii.Ltr_x).Add_byte_apos();
|
||||
gplx.core.encoders.Hex_utl_.Encode_bfr(sortkey_val_bfr, collation_mgr.Get_sortkey(tmp_sortkey));
|
||||
sortkey_val_bfr.Add_byte_apos();
|
||||
}
|
||||
else
|
||||
sortkey_val_bfr.Add_byte_apos().Add_byte_apos();
|
||||
}
|
||||
else
|
||||
sortkey_val_bfr.Add_byte_apos().Add(Db_sql_.Escape_arg(tmp_sortkey)).Add_byte_apos();
|
||||
return sortkey_val_bfr.To_bry_and_clear();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import org.junit.*; import gplx.core.tests.*; import gplx.xowa.apps.urls.*;
|
||||
import gplx.xowa.langs.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.langs.*;
|
||||
public class Xoctg_catlink_loader__tst {
|
||||
private final Xoctg_catlink_loader__fxt fxt = new Xoctg_catlink_loader__fxt();
|
||||
@Test public void Build_sortkey_val__v4() { // PURPOSE: remove "\n" and afterwards else will omit 1 record
|
||||
fxt.Test__build_sortkey_sql(4, "A\nA", "x'41'"); // fails if "x'410a41'"
|
||||
}
|
||||
@Test public void Build_sortkey_val__v2() { // PURPOSE: remove "\n" and afterwards else SQL will be malformed
|
||||
fxt.Test__build_sortkey_sql(2, "A\nA", "'A'"); // fails if "'A\nA'"
|
||||
}
|
||||
}
|
||||
class Xoctg_catlink_loader__fxt {
|
||||
public void Test__build_sortkey_sql(int version, String sortkey, String expd) {
|
||||
Xoae_app app = Xoa_app_fxt.Make__app__edit();
|
||||
Xowe_wiki wiki = Xoa_app_fxt.Make__wiki__edit(app, "de.wikipedia.org"); // use "de.wikipedia.org" for simple "uppercase" collation
|
||||
Xoctg_collation_mgr collation_mgr = new Xoctg_collation_mgr(wiki);
|
||||
|
||||
Bry_bfr bfr = Bry_bfr_.New();
|
||||
Gftest.Eq__str(expd, Xoctg_catlink_loader.Build_sortkey_val(bfr, Byte_.By_int(version), collation_mgr, Bry_.new_u8(sortkey)));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,71 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.dbs.*; import gplx.xowa.wikis.data.*; import gplx.xowa.wikis.data.tbls.*; import gplx.xowa.addons.wikis.ctgs.dbs.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.urls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.dbs.*;
|
||||
public class Xoctg_catpage_loader {
|
||||
public Xoctg_catpage_ctg Load_ctg_or_null(Xow_wiki wiki, Xoctg_catpage_mgr catpage_mgr, Xoctg_catpage_url cat_url, Xoa_ttl cat_ttl, int limit) {
|
||||
// get cat_id from page_tbl
|
||||
Xow_db_mgr db_mgr = wiki.Data__core_mgr();
|
||||
Xowd_page_tbl page_tbl = db_mgr.Db__core().Tbl__page();
|
||||
Xowd_page_itm page_itm = page_tbl.Select_by_ttl_as_itm_or_null(cat_ttl);
|
||||
if (page_itm == null) {
|
||||
Gfo_usr_dlg_.Instance.Warn_many("", "", "category does not exist in page table; ttl=~{0}", cat_ttl.Full_db());
|
||||
return null;
|
||||
}
|
||||
int cat_id = page_itm.Id();
|
||||
|
||||
// get cat_core_itm from cat_core_tbl
|
||||
Xowd_cat_core_tbl cat_core_tbl = Xodb_cat_db_.Get_cat_core_or_fail(db_mgr);
|
||||
Xowd_category_itm cat_core_itm = cat_core_tbl.Select(cat_id);
|
||||
if (cat_core_itm == Xowd_category_itm.Null) {
|
||||
Gfo_usr_dlg_.Instance.Log_many("", "", "category does not exist in cat_core table; ttl=~{0}", cat_ttl.Full_db()); // NOTE: this is not rare as Category pages can be created as deliberately empty, or as redirects; fr.w:Catégorie:Utilisateur_hess-4; DATE:2016-09-12
|
||||
return null;
|
||||
}
|
||||
|
||||
// load itms from cat_link_db for each grp_tid
|
||||
Xoctg_catpage_ctg rv = new Xoctg_catpage_ctg(cat_id, cat_ttl.Page_txt());
|
||||
for (byte grp_tid = Xoa_ctg_mgr.Tid__subc; grp_tid < Xoa_ctg_mgr.Tid___max; ++grp_tid) {
|
||||
Xoctg_catpage_grp grp = rv.Grp_by_tid(grp_tid);
|
||||
grp.Count_all_(cat_core_itm.Count_by_tid(grp_tid)); // set total counts per grp based on cat_core_itm;
|
||||
|
||||
// init url_vars
|
||||
boolean url_is_from = cat_url.Grp_fwds()[grp_tid]; // EX: "pagefrom=A"; "pageuntil=B"
|
||||
byte[] url_sortkey = cat_url.Grp_keys()[grp_tid];
|
||||
|
||||
// set prev / next props to dflt values
|
||||
if (url_is_from) { // url is from; EX: from=A
|
||||
if (Bry_.Len_eq_0(url_sortkey)) // no sortkey specified for group, so group always starts with 1st itm -> disable previous link
|
||||
grp.Prev_disable_(true);
|
||||
}
|
||||
else { // url is until; EX: until=A
|
||||
grp.Prev_disable_(true); // default prev link to disabled; loader will load 201 items and set to false if 201st found
|
||||
grp.Next_sortkey_(url_sortkey); // next sortkey is always sortkey of until url arg;
|
||||
}
|
||||
|
||||
// load links
|
||||
Xoctg_catlink_loader loader = new Xoctg_catlink_loader();
|
||||
if (cat_core_itm.File_idx() == -1) // v3 or v4: loop over all cat_link dbs {
|
||||
loader.Make_attach_mgr__v3_v4 (db_mgr, cat_core_tbl.Conn());
|
||||
else // v2: use cat_link_db
|
||||
loader.Make_attach_mgr__v2 (db_mgr, cat_core_itm.File_idx());
|
||||
loader.Run(rv, wiki, catpage_mgr, page_tbl, cat_id, grp_tid, url_is_from, url_sortkey, limit);
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.dbs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.dbs.*; import gplx.xowa.wikis.data.tbls.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*;
|
||||
public class Xoctg_page_loader implements Select_in_cbk {
|
||||
private final Xow_wiki wiki;
|
||||
private final Ordered_hash hash = Ordered_hash_.New();
|
||||
public Xoctg_page_loader(Xow_wiki wiki) {this.wiki = wiki;}
|
||||
public Ordered_hash Hash() {return hash;}
|
||||
public int Hash_max() {return hash.Len();}
|
||||
public void Write_sql(Bry_bfr bfr, int idx) {
|
||||
Xoctg_catpage_itm itm = (Xoctg_catpage_itm)hash.Get_at(idx);
|
||||
bfr.Add_int_variable(itm.Page_id());
|
||||
}
|
||||
public void Read_data(Db_rdr rdr) {
|
||||
// read values from page_tbl
|
||||
int page_id = rdr.Read_int("page_id");
|
||||
int page_ns = rdr.Read_int("page_namespace");
|
||||
byte[] page_ttl = rdr.Read_bry_by_str("page_title");
|
||||
|
||||
// get itm and set data
|
||||
Xoctg_catpage_itm itm = (Xoctg_catpage_itm)hash.Get_by(page_id);
|
||||
if (itm == null) return; // NOTE: itms can exist in cat_links_tbl, but not in page_tbl; EX:User:Any_page
|
||||
itm.Page_ttl_(wiki.Ttl_parse(page_ns, page_ttl));
|
||||
}
|
||||
}
|
||||
@@ -17,12 +17,15 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
public class Xoctg_catpage_ctg {
|
||||
public Xoctg_catpage_ctg(byte[] name) {this.name = name;}
|
||||
public byte[] Name() {return name;} private final byte[] name;
|
||||
public Xoctg_catpage_grp Subcs() {return subcs;} private final Xoctg_catpage_grp subcs = new Xoctg_catpage_grp(Xoa_ctg_mgr.Tid__subc);
|
||||
public Xoctg_catpage_grp Pages() {return pages;} private final Xoctg_catpage_grp pages = new Xoctg_catpage_grp(Xoa_ctg_mgr.Tid__page);
|
||||
public Xoctg_catpage_grp Files() {return files;} private final Xoctg_catpage_grp files = new Xoctg_catpage_grp(Xoa_ctg_mgr.Tid__file);
|
||||
public int Total() {return subcs.Itms__len() + pages.Itms__len() + files.Itms__len();}
|
||||
public Xoctg_catpage_ctg(int id, byte[] name) {
|
||||
this.id = id; this.name = name;
|
||||
}
|
||||
public int Id() {return id;} private final int id;
|
||||
public byte[] Name() {return name;} private final byte[] name;
|
||||
public Xoctg_catpage_grp Subcs() {return subcs;} private final Xoctg_catpage_grp subcs = new Xoctg_catpage_grp(Xoa_ctg_mgr.Tid__subc);
|
||||
public Xoctg_catpage_grp Pages() {return pages;} private final Xoctg_catpage_grp pages = new Xoctg_catpage_grp(Xoa_ctg_mgr.Tid__page);
|
||||
public Xoctg_catpage_grp Files() {return files;} private final Xoctg_catpage_grp files = new Xoctg_catpage_grp(Xoa_ctg_mgr.Tid__file);
|
||||
public int Total() {return subcs.Count_all() + pages.Count_all() + files.Count_all();}
|
||||
public Xoctg_catpage_grp Grp_by_tid(byte tid) {
|
||||
switch (tid) {
|
||||
case Xoa_ctg_mgr.Tid__subc: return subcs;
|
||||
@@ -31,10 +34,4 @@ public class Xoctg_catpage_ctg {
|
||||
default: throw Err_.new_unhandled(tid);
|
||||
}
|
||||
}
|
||||
public void Make_itms() {
|
||||
for (byte i = 0; i < Xoa_ctg_mgr.Tid___max; ++i) {
|
||||
Xoctg_catpage_grp grp = Grp_by_tid(i);
|
||||
grp.Itms__make();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,27 +17,38 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
public class Xoctg_catpage_grp {
|
||||
private final List_adp tmp_list = List_adp_.New();
|
||||
private Xoctg_catpage_itm[] itms = Xoctg_catpage_itm.Ary_empty;
|
||||
private byte[] next_sortkey = Bry_.Empty;
|
||||
public Xoctg_catpage_grp(byte tid) {this.tid = tid;}
|
||||
public byte Tid() {return tid;} private byte tid; // subc|page|file
|
||||
public int Bgn() {return bgn;} private int bgn; // idx of 1st item; EX: 200
|
||||
public int End() {return end;} private int end; // idx of nth item + 1; EX: 399
|
||||
public int Count_by_page() {return end - bgn;} // count of items on page; EX: 200
|
||||
public int Itms__len() {return itms_len;} private int itms_len; // count of items in entire category; EX: 456
|
||||
public Xoctg_catpage_itm[] Itms() {return itms;} private Xoctg_catpage_itm[] itms = Xoctg_catpage_itm.Ary_empty;
|
||||
public Xoctg_catpage_itm Itms__get_at(int i) {
|
||||
if (i < 0 || i >= itms.length) throw Err_.new_wo_type("catpage: i is out of bounds", "i", i, "len", itms.length, "tid", tid);
|
||||
Xoctg_catpage_itm rv = itms[i]; if (rv == null) throw Err_.new_wo_type("ctg.view: itm is null", "i", i, "len", itms.length, "tid", tid);
|
||||
return rv;
|
||||
public byte Tid() {return tid;} private byte tid; // subc|page|file
|
||||
public int Count_all() {return count_all;} private int count_all; // count of items in entire category; EX: 456
|
||||
public boolean Prev_disable() {return prev_disable;} private boolean prev_disable; // prev_link: disable link
|
||||
public byte[] Next_sortkey() {return next_sortkey;} // next_link: set sortkey
|
||||
public int Itms__len() {return itms.length;}
|
||||
public Xoctg_catpage_itm Itms__get_at(int i) {return itms[i];}
|
||||
|
||||
public void Count_all_(int v) {this.count_all = v;}
|
||||
public void Prev_disable_(boolean v) {this.prev_disable = v;}
|
||||
public void Next_sortkey_(byte[] v) {this.next_sortkey = v;}
|
||||
public void Itms_(Xoctg_catpage_itm[] v) {
|
||||
this.itms = v;
|
||||
Array_.Sort(itms, new Xoctg_catpage_itm_sorter()); // NOTE: need to reorder for page_until b/c ORDER BY DESC
|
||||
|
||||
// make sortkey_handle
|
||||
Bry_bfr tmp_bfr = Bry_bfr_.New();
|
||||
int itms_len = itms.length;
|
||||
byte[] prv_sortkey_handle = Bry_.Empty;
|
||||
for (int i = 0; i < itms_len; ++i) {
|
||||
Xoctg_catpage_itm itm = itms[i];
|
||||
prv_sortkey_handle = itm.Sortkey_handle_make(tmp_bfr, prv_sortkey_handle);
|
||||
}
|
||||
}
|
||||
public void Itms__add(Xoctg_catpage_itm sub) {tmp_list.Add(sub);}
|
||||
public void Itms__make() {
|
||||
tmp_list.Sort_by(Xoctg_catpage_itm_sorter__sort_key.Sorter);
|
||||
itms = (Xoctg_catpage_itm[])tmp_list.To_ary_and_clear(Xoctg_catpage_itm.class);
|
||||
bgn = 0;
|
||||
end = itms_len = itms.length;
|
||||
}
|
||||
public void Rng_(int bgn, int end) {
|
||||
this.bgn = bgn; this.end = end;
|
||||
|
||||
}
|
||||
class Xoctg_catpage_itm_sorter implements gplx.core.lists.ComparerAble {
|
||||
public int compare(Object lhsObj, Object rhsObj) {
|
||||
Xoctg_catpage_itm lhs = (Xoctg_catpage_itm)lhsObj;
|
||||
Xoctg_catpage_itm rhs = (Xoctg_catpage_itm)rhsObj;
|
||||
return Bry_.Compare(lhs.Sortkey_binary(), rhs.Sortkey_binary());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -16,17 +16,86 @@ You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.dbs.*; import gplx.xowa.wikis.nss.*;
|
||||
public class Xoctg_catpage_itm {
|
||||
public Xoctg_catpage_itm(int page_id, Xoa_ttl page_ttl, byte[] sort_key) {
|
||||
private byte version;
|
||||
Xoctg_catpage_itm(byte version, byte grp_tid, int page_id, byte[] sortkey_prefix, byte[] sortkey_binary) {
|
||||
this.version = version;
|
||||
this.grp_tid = grp_tid;
|
||||
this.page_id = page_id;
|
||||
this.page_ttl = page_ttl;
|
||||
this.sort_key = sort_key.length == 0 ? page_ttl.Page_db() : sort_key; // v1 will not have sortkey data; PAGE:s.w:Category:Computer_science DATE:2015-11-22
|
||||
this.page_ttl = Xoa_ttl.Null;
|
||||
this.sortkey_prefix = sortkey_prefix;
|
||||
this.sortkey_handle = sortkey_prefix; // default handle to sortkey_prefix;
|
||||
this.sortkey_binary = sortkey_binary;
|
||||
}
|
||||
public byte Grp_tid() {return grp_tid;} private final byte grp_tid; // v2-v4:cl_type_id; subc,page,file
|
||||
public int Page_id() {return page_id;} private final int page_id; // v2-v4:cl_from
|
||||
public byte[] Sortkey_prefix() {return sortkey_prefix;} private byte[] sortkey_prefix; // v2-v3:cl_sortkey; v4:cl_sortkey_prefix
|
||||
public byte[] Sortkey_handle() {return sortkey_handle;} private byte[] sortkey_handle; // v2-v3:cl_sortkey; v4:cl_sortkey_prefix\nttl_txt; never "cl_sortkey" which is binary ICU value;
|
||||
public byte[] Sortkey_binary() {return sortkey_binary;} private byte[] sortkey_binary; // v2-v4:cl_sortkey; note that v4 is binary icu value
|
||||
public Xoa_ttl Page_ttl() {return page_ttl;} private Xoa_ttl page_ttl;
|
||||
|
||||
public void Page_ttl_(Xoa_ttl ttl) {
|
||||
this.page_ttl = ttl;
|
||||
// sortkey_prefix will be blank for v2; use page_ttl; PAGE:s.w:Category:Computer_science DATE:2015-11-22
|
||||
if (version == Version__2 && Bry_.Len_eq_0(sortkey_prefix))
|
||||
sortkey_prefix = page_ttl.Page_txt();
|
||||
|
||||
// sortkey_binary will be blank for v2,v3; use page_ttl; PAGE:fr.w:Article_contenant_un_appel_à_traduction_en_anglais; DATE:2016-10-11
|
||||
if (version != Version__4 && Bry_.Len_eq_0(sortkey_binary)) sortkey_binary = page_ttl.Page_txt();
|
||||
}
|
||||
public byte[] Sortkey_handle_make(Bry_bfr tmp_bfr, byte[] prv_sortkey_handle) {
|
||||
// page.tbl missing even though in cat_link.tbl; happens for "User:" namespace pages;
|
||||
if (page_ttl == Xoa_ttl.Null) {
|
||||
// sortkey_prefix exists; happens for [[Category:A]] as opposed to [[Category:A|some_sortkey_prefix]]
|
||||
if (Bry_.Len_gt_0(sortkey_prefix)) {
|
||||
sortkey_handle = sortkey_prefix;
|
||||
return sortkey_handle; // set sortkey_prefix as new prv_sortkey_handle;
|
||||
}
|
||||
else {
|
||||
// set sortkey_handle to "prv_sortkey" + "page_id"; needed for multiple "missing" catlinks which span 200 page boundaries
|
||||
tmp_bfr.Add(prv_sortkey_handle);
|
||||
tmp_bfr.Add_byte_nl();
|
||||
tmp_bfr.Add_int_variable(page_id);
|
||||
sortkey_handle = tmp_bfr.To_bry_and_clear();
|
||||
return prv_sortkey_handle;
|
||||
}
|
||||
}
|
||||
// page.tbl exists
|
||||
else {
|
||||
// "In UCA, tab is the only character that can sort above LF so we strip both of them from the original prefix."; Title.php|getCategorySortKey
|
||||
if (sortkey_prefix.length == 0) {
|
||||
sortkey_handle = page_ttl.Page_txt();
|
||||
}
|
||||
else {
|
||||
byte[] sortkey_normalized = Bry_.Replace(sortkey_prefix, Sortkey_prefix_replace__src, Sortkey_prefix_replace__trg);
|
||||
tmp_bfr.Add(sortkey_normalized);
|
||||
tmp_bfr.Add_byte_nl().Add(page_ttl.Page_txt()); // "$prefix\n$unprefixed";
|
||||
sortkey_handle = tmp_bfr.To_bry_and_clear();
|
||||
}
|
||||
return sortkey_handle;
|
||||
}
|
||||
}
|
||||
public int Page_id() {return page_id;} private int page_id;
|
||||
public Xoa_ttl Page_ttl() {return page_ttl;} private Xoa_ttl page_ttl;
|
||||
public byte[] Sort_key() {return sort_key;} private byte[] sort_key;
|
||||
public boolean Missing() {return missing;} private boolean missing; // not used; remove?;
|
||||
public void Missing_y_() {missing = true;}
|
||||
|
||||
public static final Xoctg_catpage_itm[] Ary_empty = new Xoctg_catpage_itm[0];
|
||||
public static Xoctg_catpage_itm New_by_rdr(Db_rdr rdr, byte version) {
|
||||
byte[] sortkey_binary = Bry_.Empty;
|
||||
byte[] sortkey_prefix = Bry_.Empty;
|
||||
if (version == Version__4) {
|
||||
sortkey_binary = rdr.Read_bry("cl_sortkey");
|
||||
sortkey_prefix = rdr.Read_bry_by_str("cl_sortkey_prefix");
|
||||
}
|
||||
else {
|
||||
sortkey_binary = Bry_.Empty;
|
||||
sortkey_prefix = rdr.Read_bry_by_str("cl_sortkey");
|
||||
}
|
||||
return new Xoctg_catpage_itm(version, rdr.Read_byte("cl_type_id"), rdr.Read_int("cl_from"), sortkey_prefix, sortkey_binary);
|
||||
}
|
||||
public static Xoctg_catpage_itm New_by_ttl(byte grp_tid, int page_id, Xoa_ttl ttl) { // TEST
|
||||
Xoctg_catpage_itm rv = new Xoctg_catpage_itm(Version__4, grp_tid, page_id, ttl.Page_txt(), Bry_.Empty);
|
||||
rv.Page_ttl_(ttl);
|
||||
return rv;
|
||||
}
|
||||
private static final byte Version__2 = 2, Version__4 = 4;
|
||||
private static final byte[] Sortkey_prefix_replace__src = Bry_.new_a7("\n\t"), Sortkey_prefix_replace__trg = Bry_.new_a7(" ");
|
||||
}
|
||||
|
||||
@@ -16,15 +16,28 @@ You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
public class Xoctg_catpage_itm_sorter__sort_key implements gplx.core.lists.ComparerAble, gplx.core.lists.binary_searches.Binary_comparer {
|
||||
public int compare(Object lhsObj, Object rhsObj) {
|
||||
Xoctg_catpage_itm lhs = (Xoctg_catpage_itm)lhsObj;
|
||||
Xoctg_catpage_itm rhs = (Xoctg_catpage_itm)rhsObj;
|
||||
return Bry_.Compare(lhs.Sort_key(), rhs.Sort_key());
|
||||
public class Xoctg_catpage_tmp {
|
||||
private final List_adp subc_list = List_adp_.New(), page_list = List_adp_.New(), file_list = List_adp_.New();
|
||||
public void Add(Xoctg_catpage_itm itm) {
|
||||
List_adp list = Get_by_tid(itm.Grp_tid());
|
||||
list.Add(itm);
|
||||
}
|
||||
public int Compare_val_to_obj(Object val, Object obj) {
|
||||
Xoctg_catpage_itm itm = (Xoctg_catpage_itm)obj;
|
||||
return Bry_.Compare((byte[])val, itm.Sort_key());
|
||||
public void Make_by_ctg(Xoctg_catpage_ctg ctg) { // TEST:
|
||||
for (byte tid = 0; tid < Xoa_ctg_mgr.Tid___max; ++tid)
|
||||
Make_by_grp(ctg.Grp_by_tid(tid));
|
||||
}
|
||||
public void Make_by_grp(Xoctg_catpage_grp grp) {
|
||||
byte tid = grp.Tid();
|
||||
List_adp list = Get_by_tid(tid);
|
||||
if (list.Len() == 0) return;
|
||||
grp.Itms_((Xoctg_catpage_itm[])list.To_ary_and_clear(Xoctg_catpage_itm.class));
|
||||
}
|
||||
private List_adp Get_by_tid(byte tid) {
|
||||
switch (tid) {
|
||||
case Xoa_ctg_mgr.Tid__subc: return subc_list;
|
||||
case Xoa_ctg_mgr.Tid__page: return page_list;
|
||||
case Xoa_ctg_mgr.Tid__file: return file_list;
|
||||
default: throw Err_.new_unhandled_default(tid);
|
||||
}
|
||||
}
|
||||
public static final Xoctg_catpage_itm_sorter__sort_key Sorter = new Xoctg_catpage_itm_sorter__sort_key();
|
||||
}
|
||||
@@ -16,7 +16,7 @@ You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.fmts; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.xowa.langs.*; import gplx.xowa.langs.msgs.*; import gplx.xowa.htmls.core.htmls.*; import gplx.langs.htmls.encoders.*;
|
||||
import gplx.xowa.langs.*; import gplx.xowa.langs.msgs.*; import gplx.xowa.htmls.core.htmls.*; import gplx.langs.htmls.encoders.*; import gplx.core.intls.ucas.*;
|
||||
import gplx.xowa.wikis.nss.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.urls.*;
|
||||
public class Xoctg_fmt_grp { // subc|page|file
|
||||
@@ -32,47 +32,43 @@ public class Xoctg_fmt_grp { // subc|page|file
|
||||
this.url_arg_bgn = url_arg_bgn; this.url_arg_end = url_arg_end; this.div_id = div_id;
|
||||
}
|
||||
public Xoctg_fmt_itm_base Itm_fmt() {return itm_fmt;} private final Xoctg_fmt_itm_base itm_fmt;
|
||||
public void Write_catpage_grp(Bry_bfr bfr, Xow_wiki wiki, Xol_lang_itm lang, Xoctg_catpage_ctg dom_ctg, int grp_max) { // TEST:
|
||||
public void Write_catpage_grp(Bry_bfr bfr, Xow_wiki wiki, Xol_lang_itm lang, Uca_ltr_extractor ltr_extractor, Xoctg_catpage_ctg dom_ctg, int grp_max) { // TEST:
|
||||
Xoctg_catpage_grp dom_grp = dom_ctg.Grp_by_tid(tid);
|
||||
if (dom_grp.Itms__len() == 0) return; // no items in grp; EX: 0 items in File
|
||||
if (dom_grp.Count_all() == 0) return; // no items in grp; EX: 0 items in File
|
||||
|
||||
// get msgs
|
||||
Xow_msg_mgr msg_mgr = wiki.Msg_mgr();
|
||||
byte[] msg_label_bry = msg_mgr.Val_by_id_args(msg_label_id, dom_ctg.Name());
|
||||
byte[] msg_stats_bry = msg_mgr.Val_by_id_args(msg_stats_id, dom_grp.Count_by_page(), dom_grp.Itms__len());
|
||||
byte[] msg_stats_bry = msg_mgr.Val_by_id_args(msg_stats_id, dom_grp.Itms__len(), dom_grp.Count_all());
|
||||
|
||||
// get nav html; next / previous 200
|
||||
Xoa_ttl ctg_ttl = wiki.Ttl_parse(Xow_ns_.Tid__category, dom_ctg.Name());
|
||||
byte[] nav_html = this.Bld_bwd_fwd(wiki, ctg_ttl, dom_grp, grp_max);
|
||||
|
||||
// init grp; write
|
||||
itms_fmt.Init_from_grp(wiki, dom_grp);
|
||||
itms_fmt.Init_from_grp(wiki, dom_grp, ltr_extractor);
|
||||
Fmt__ctg.Bld_many(bfr, div_id, msg_label_bry, msg_stats_bry, nav_html, lang.Key_bry(), lang.Dir_ltr_bry(), itms_fmt);
|
||||
}
|
||||
public byte[] Bld_bwd_fwd(Xow_wiki wiki, Xoa_ttl ttl, Xoctg_catpage_grp view_grp, int grp_max) { // TEST:
|
||||
if (view_grp.Itms__len() < grp_max) return Bry_.Empty; // < 200; never show;
|
||||
if (view_grp.Count_all() < grp_max) return Bry_.Empty; // < 200; never show;
|
||||
Bry_bfr bfr = wiki.Utl__bfr_mkr().Get_k004();
|
||||
Html_nav_bry(bfr, wiki, ttl, view_grp, grp_max, Bool_.N);
|
||||
Html_nav_bry(bfr, wiki, ttl, view_grp, grp_max, Bool_.Y);
|
||||
return bfr.To_bry_and_rls();
|
||||
}
|
||||
private void Html_nav_bry(Bry_bfr bfr, Xow_wiki wiki, Xoa_ttl ttl, Xoctg_catpage_grp grp, int grp_max, boolean type_is_next) {
|
||||
private void Html_nav_bry(Bry_bfr bfr, Xow_wiki wiki, Xoa_ttl ttl, Xoctg_catpage_grp grp, int grp_max, boolean url_is_from) {
|
||||
Bry_bfr href_bfr = wiki.Utl__bfr_mkr().Get_b512();
|
||||
|
||||
// get nav_href; EX:href="/wiki/Category:Ctg_1?pageuntil=A1#mw-pages"
|
||||
wiki.Html__href_wtr().Build_to_bfr(href_bfr, wiki.App(), Xoh_wtr_ctx.Basic, wiki.Domain_bry(), ttl);
|
||||
byte[] arg_idx_lbl = null; byte[] arg_sortkey = null;
|
||||
if (type_is_next) {
|
||||
if (url_is_from) {
|
||||
arg_idx_lbl = url_arg_bgn;
|
||||
|
||||
// get next category after last one on page; needed for "Next 200 (href=Cat_201)"
|
||||
int nxt_idx = grp.End();
|
||||
if (nxt_idx == grp.Itms__len()) --nxt_idx; // if last item, then grp.End() does not exist; just use last one
|
||||
arg_sortkey = grp.Itms__get_at(nxt_idx).Sort_key();
|
||||
arg_sortkey = grp.Next_sortkey();
|
||||
}
|
||||
else {
|
||||
arg_idx_lbl = url_arg_end;
|
||||
arg_sortkey = grp.Itms__get_at(grp.Bgn()).Sort_key(); // use 1st item as sortkey for "until" args
|
||||
arg_sortkey = grp.Itms__get_at(0).Sortkey_handle(); // use 1st item as sortkey for "until" args
|
||||
}
|
||||
href_bfr.Add_byte(Byte_ascii.Question).Add(arg_idx_lbl).Add_byte(Byte_ascii.Eq); // filefrom=
|
||||
Gfo_url_encoder_.Http_url.Encode(href_bfr, arg_sortkey); // Abc
|
||||
@@ -80,12 +76,12 @@ public class Xoctg_fmt_grp { // subc|page|file
|
||||
byte[] nav_href = href_bfr.To_bry_and_rls();
|
||||
|
||||
// get nav_text
|
||||
int nav_text_id = type_is_next ? Xol_msg_itm_.Id_next_results : Xol_msg_itm_.Id_prev_results;
|
||||
int nav_text_id = url_is_from ? Xol_msg_itm_.Id_next_results : Xol_msg_itm_.Id_prev_results;
|
||||
byte[] nav_text = wiki.Msg_mgr().Val_by_id_args(nav_text_id, grp_max); // next 200 / previous 200
|
||||
|
||||
// print text if 1st / zth page; else, print html
|
||||
if ( ( type_is_next && grp.Bgn() + grp_max > grp.Itms__len())
|
||||
|| (!type_is_next && grp.Bgn() - grp_max < 0)
|
||||
if ( ( url_is_from && Bry_.Len_eq_0(grp.Next_sortkey()))
|
||||
|| (!url_is_from && grp.Prev_disable())
|
||||
)
|
||||
Fmt__nav__text.Bld_many(bfr, nav_text);
|
||||
else
|
||||
|
||||
@@ -17,27 +17,32 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.fmts; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.langs.htmls.*; import gplx.xowa.htmls.*; import gplx.xowa.htmls.hrefs.*; import gplx.xowa.htmls.core.wkrs.lnkis.htmls.*; import gplx.xowa.htmls.core.htmls.*;
|
||||
import gplx.xowa.langs.*; import gplx.xowa.langs.msgs.*;
|
||||
import gplx.xowa.langs.*; import gplx.xowa.langs.msgs.*; import gplx.core.intls.ucas.*;
|
||||
import gplx.xowa.users.history.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*;
|
||||
public abstract class Xoctg_fmt_itm_base implements gplx.core.brys.Bfr_arg {
|
||||
private final Bry_bfr tmp_bfr = Bry_bfr_.New();
|
||||
private Xow_wiki wiki;
|
||||
private Xoctg_catpage_grp grp;
|
||||
private Uca_ltr_extractor ltr_extractor;
|
||||
private byte[] ltr_cur; private int loop_bgn; private int col_end;
|
||||
|
||||
public int Loop_end_idx() {return loop_end_idx;} private int loop_end_idx;
|
||||
public boolean Loop_ends_at_col() {return loop_ends_at_col;} private boolean loop_ends_at_col;
|
||||
public void Col_end_(int col_bgn, int col_idx) {
|
||||
this.col_end = col_bgn + Calc_col_len(grp.Count_by_page(), col_idx, Cols_max);
|
||||
this.col_end = col_bgn + Calc_col_len(grp.Itms__len(), col_idx, Cols_max);
|
||||
}
|
||||
public void Init_from_ltr(Xow_wiki wiki, Xoctg_catpage_grp grp, Uca_ltr_extractor ltr_extractor) {
|
||||
this.wiki = wiki;
|
||||
this.grp = grp;
|
||||
this.ltr_extractor = ltr_extractor;
|
||||
}
|
||||
public void Init_from_ltr(Xow_wiki wiki, Xoctg_catpage_grp grp) {this.wiki = wiki; this.grp = grp;}
|
||||
public void Set_ltr_and_bgn(byte[] ltr_cur, int loop_bgn) {this.ltr_cur = ltr_cur; this.loop_bgn = loop_bgn;}
|
||||
public void Bfr_arg__add(Bry_bfr bfr) {
|
||||
// init vars
|
||||
Xoh_href_parser href_parser = wiki.App().Html__href_parser();
|
||||
Xou_history_mgr history_mgr = wiki.App().User().History_mgr();
|
||||
int grp_end = grp.End();
|
||||
int grp_end = grp.Itms__len();
|
||||
|
||||
// loop over itms;
|
||||
for (int i = loop_bgn; i < grp_end; i++) {
|
||||
@@ -50,28 +55,30 @@ public abstract class Xoctg_fmt_itm_base implements gplx.core.brys.Bfr_arg {
|
||||
|
||||
// get sortkey
|
||||
Xoctg_catpage_itm itm = grp.Itms__get_at(i);
|
||||
byte[] itm_sortkey = itm.Sort_key();
|
||||
byte[] itm_sortkey = itm.Sortkey_handle();
|
||||
|
||||
// reached end of ltr; exit
|
||||
if (!Bry_.Has_at_bgn(itm_sortkey, ltr_cur, 0, itm_sortkey.length)) {
|
||||
byte[] ltr_1st = ltr_extractor.Get_1st_ltr(itm_sortkey);
|
||||
if (!Bry_.Has_at_bgn(ltr_1st, ltr_cur, 0, ltr_1st.length)) {
|
||||
loop_end_idx = i;
|
||||
loop_ends_at_col = i == col_end;
|
||||
return;
|
||||
}
|
||||
|
||||
Bld_html(bfr, wiki, history_mgr, href_parser, itm, itm.Page_ttl());
|
||||
Xoa_ttl itm_ttl = itm.Page_ttl();
|
||||
Bld_html(bfr, wiki, history_mgr, href_parser, itm, itm_ttl);
|
||||
}
|
||||
loop_end_idx = grp_end;
|
||||
loop_ends_at_col = true;
|
||||
}
|
||||
@gplx.Virtual public void Bld_html(Bry_bfr bfr, Xow_wiki wiki, Xou_history_mgr history_mgr, Xoh_href_parser href_parser, Xoctg_catpage_itm itm, Xoa_ttl ttl) {
|
||||
byte[] itm_full_ttl = Gfh_utl.Escape_html_as_bry(tmp_bfr, ttl.Full_txt_w_ttl_case());// NOTE: ttl.Full_txt() to get full ns; EX: Template:A instead of just "A"
|
||||
if (itm.Missing())
|
||||
fmt_missing.Bld_many(bfr, itm.Page_id(), itm_full_ttl);
|
||||
if (ttl == Xoa_ttl.Null)
|
||||
fmt_missing.Bld_many(bfr, itm.Page_id(), itm.Sortkey_handle());
|
||||
else {
|
||||
byte[] itm_full_ttl = Gfh_utl.Escape_html_as_bry(tmp_bfr, ttl.Full_txt_w_ttl_case());// NOTE: ttl.Full_txt() to get full ns; EX: Template:A instead of just "A"
|
||||
byte[] itm_href = wiki.Html__href_wtr().Build_to_bry(wiki, ttl);
|
||||
byte[] itm_atr_cls = Xoh_lnki_wtr.Lnki_cls_visited(history_mgr, wiki.Domain_bry(), ttl.Page_txt()); // NOTE: must be ttl.Page_txt() in order to match Xou_history_mgr.Add
|
||||
fmt_exists.Bld_many(bfr, itm_href, itm_atr_cls, itm_full_ttl, itm_full_ttl);
|
||||
fmt_exists.Bld_many(bfr, itm_href, itm_atr_cls, itm_full_ttl, itm_full_ttl, gplx.core.encoders.Hex_utl_.Encode_bry(itm.Sortkey_binary()));
|
||||
}
|
||||
}
|
||||
private static final Bry_fmt
|
||||
@@ -81,7 +88,7 @@ public abstract class Xoctg_fmt_itm_base implements gplx.core.brys.Bfr_arg {
|
||||
)
|
||||
, fmt_exists = Bry_fmt.Auto_nl_skip_last
|
||||
( ""
|
||||
, " <li><a href=\"~{itm_href}\"~{itm_atr_cls} title=\"~{itm_title}\">~{itm_text}</a></li>"
|
||||
, " <li><a href=\"~{itm_href}\"~{itm_atr_cls} title=\"~{itm_title}\">~{itm_text}</a><!--~{itm_sortkey}--></li>"
|
||||
)
|
||||
;
|
||||
public static final int Cols_max = 3;
|
||||
|
||||
@@ -17,23 +17,25 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.fmts; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.xowa.htmls.core.htmls.*;
|
||||
import gplx.xowa.langs.*; import gplx.xowa.langs.msgs.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*;
|
||||
import gplx.xowa.langs.*; import gplx.xowa.langs.msgs.*; import gplx.core.intls.ucas.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*;
|
||||
public class Xoctg_fmt_ltr implements gplx.core.brys.Bfr_arg { // "A", "B", "C cont."
|
||||
private final Xoctg_fmt_itm_base itm_fmt;
|
||||
private Xoctg_catpage_grp grp;
|
||||
private byte[] msg__list_continues;
|
||||
private Uca_ltr_extractor ltr_extractor;
|
||||
public Xoctg_fmt_ltr(Xoctg_fmt_itm_base itm_fmt) {
|
||||
this.itm_fmt = itm_fmt;
|
||||
}
|
||||
public void Init_from_grp(Xow_wiki wiki, Xoctg_catpage_grp grp) {
|
||||
public void Init_from_grp(Xow_wiki wiki, Xoctg_catpage_grp grp, Uca_ltr_extractor ltr_extractor) {
|
||||
this.grp = grp;
|
||||
this.msg__list_continues = wiki.Msg_mgr().Val_by_id(Xol_msg_itm_.Id_list_continues);
|
||||
itm_fmt.Init_from_ltr(wiki, grp);
|
||||
this.ltr_extractor = ltr_extractor;
|
||||
itm_fmt.Init_from_ltr(wiki, grp, ltr_extractor);
|
||||
}
|
||||
public void Bfr_arg__add(Bry_bfr bfr) {
|
||||
int itm_idx = grp.Bgn(); // itm idx; EX: idx=201 in len=500
|
||||
int itm_end = grp.End();
|
||||
int itm_idx = 0;
|
||||
int itm_end = grp.Itms__len();
|
||||
int itms_len = itm_end - itm_idx; if (itms_len == 0) return; // no items; exit
|
||||
|
||||
int col_idx = 0; // col idx; EX: 3 cols; idx = 0, 1, 2
|
||||
@@ -45,8 +47,9 @@ public class Xoctg_fmt_ltr implements gplx.core.brys.Bfr_arg { // "A", "B", "C c
|
||||
Xoctg_catpage_itm itm = grp.Itms__get_at(itm_idx);
|
||||
|
||||
// get ltr_head; EX: "C" or "C cont."
|
||||
byte[] itm_sortkey = itm.Sort_key();
|
||||
byte[] ltr_cur = gplx.core.intls.Utf8_.Get_char_at_pos_as_bry(itm_sortkey, 0);
|
||||
byte[] itm_sortkey = itm.Sortkey_handle();
|
||||
// byte[] ltr_cur = gplx.core.intls.Utf8_.Get_char_at_pos_as_bry(itm_sortkey, 0);
|
||||
byte[] ltr_cur = ltr_extractor.Get_1st_ltr(itm_sortkey);
|
||||
byte[] ltr_head = Bry_.Eq(ltr_prv, ltr_cur)
|
||||
? Bry_.Add(ltr_prv, Byte_ascii.Space_bry, msg__list_continues) // new col uses same ltr as last itm in old col; add "cont."; EX: "C cont."
|
||||
: ltr_cur; // else, just use ltr; EX: "C"
|
||||
|
||||
@@ -0,0 +1,41 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.langs; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.core.intls.ucas.*;
|
||||
public class Xoctg_collation_mgr {
|
||||
private final Xow_wiki wiki;
|
||||
private Uca_collator collator;
|
||||
private String collation_name = "uppercase"; // REF:https://noc.wikimedia.org/conf/InitialiseSettings.php.txt|wgCategoryCollation|default
|
||||
public Xoctg_collation_mgr(Xow_wiki wiki) {
|
||||
this.wiki = wiki;
|
||||
if (String_.Eq(wiki.Domain_str(), "en.wikipedia.org"))
|
||||
collation_name = "uca-default-kn";
|
||||
}
|
||||
public void Collation_name_(String v) {
|
||||
this.collation_name = v;
|
||||
}
|
||||
public byte[] Get_sortkey(byte[] src) {
|
||||
if (String_.Eq(collation_name, "uppercase")) {
|
||||
return wiki.Lang().Case_mgr().Case_build_upper(src);
|
||||
}
|
||||
else {
|
||||
if (collator == null) collator = Uca_collator_.New(collation_name, true);
|
||||
return collator.Get_sortkey(String_.new_u8(src));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -20,4 +20,16 @@ public class Xoctg_catpage_url {
|
||||
public Xoctg_catpage_url(byte[][] keys, boolean[] fwds) {this.keys = keys; this.fwds = fwds;}
|
||||
public byte[][] Grp_keys() {return keys;} private final byte[][] keys;
|
||||
public boolean[] Grp_fwds() {return fwds;} private final boolean[] fwds;
|
||||
|
||||
public static Xoctg_catpage_url New__blank() {
|
||||
byte[][] keys = new byte[Xoa_ctg_mgr.Tid___max][];
|
||||
boolean[] fwds = new boolean[Xoa_ctg_mgr.Tid___max];
|
||||
|
||||
// for blank url, all fwds are true; EX: "Category:A" -> keys {"", "", ""}, fwds {true, true, true}
|
||||
for (int i = 0; i < Xoa_ctg_mgr.Tid___max; ++i) {
|
||||
fwds[i] = Bool_.Y;
|
||||
keys[i] = Bry_.Empty;
|
||||
}
|
||||
return new Xoctg_catpage_url(keys, fwds);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -21,15 +21,20 @@ import gplx.langs.htmls.encoders.*;
|
||||
public class Xoctg_catpage_url_parser {
|
||||
public static Xoctg_catpage_url Parse(Xoa_url url) {
|
||||
Gfo_qarg_itm[] args = url.Qargs_ary();
|
||||
if (args == null) return null;
|
||||
if (args == null) return Xoctg_catpage_url.New__blank();
|
||||
int len = args.length;
|
||||
if (len == 0) return Xoctg_catpage_url.New__blank();
|
||||
|
||||
// init caturl structs
|
||||
byte[][] keys = new byte[Xoa_ctg_mgr.Tid___max][];
|
||||
boolean[] fwds = new boolean[Xoa_ctg_mgr.Tid___max];
|
||||
for (int i = 0; i < Xoa_ctg_mgr.Tid___max; ++i) {
|
||||
fwds[i] = Bool_.Y;
|
||||
keys[i] = Bry_.Empty;
|
||||
}
|
||||
Bry_bfr tmp_bfr = Bry_bfr_.New();
|
||||
|
||||
// loop qargs; EX: "?subcatfrom=B&filefrom=C&pagefrom=D"
|
||||
int len = args.length;
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Gfo_qarg_itm arg = args[i];
|
||||
|
||||
|
||||
@@ -1,62 +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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.utls; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.core.lists.binary_searches.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.urls.*;
|
||||
public class Xoctg_catpage_filter {
|
||||
public static void Filter(int limit, Xoctg_catpage_url cat_url, Xoctg_catpage_ctg ctg) {
|
||||
int len = Xoa_ctg_mgr.Tid___max;
|
||||
for (byte i = 0; i < len; ++i) {
|
||||
Filter_by_grp(limit, cat_url, ctg.Grp_by_tid(i));
|
||||
}
|
||||
}
|
||||
private static void Filter_by_grp(int grp_len, Xoctg_catpage_url cat_url, Xoctg_catpage_grp grp) {
|
||||
byte grp_tid = grp.Tid();
|
||||
byte[] grp_key = cat_url.Grp_keys()[grp_tid];
|
||||
|
||||
// dflt to bos; EX: grp_bgn=0 grp_end=200
|
||||
int grp_bgn = 0;
|
||||
int grp_end = grp_bgn + grp_len;
|
||||
|
||||
// key specified; calc new grp_bgn, grp_end
|
||||
if (grp_key != null) {
|
||||
// get idx of key
|
||||
int key_idx = Binary_search_.Search(grp.Itms(), Xoctg_catpage_itm_sorter__sort_key.Sorter, grp_key);
|
||||
|
||||
// if fwd, set grp_bgn to key_idx, and add grp_len
|
||||
if (cat_url.Grp_fwds()[grp_tid]) {
|
||||
grp_bgn = key_idx;
|
||||
grp_end = grp_bgn + grp_len;
|
||||
}
|
||||
// if bwd, set grp_end to key_idx, and subtract grp_len
|
||||
else {
|
||||
grp_end = key_idx;
|
||||
grp_bgn = grp_end - grp_len;
|
||||
|
||||
// assert new grp_bgn is not negative
|
||||
if (grp_bgn < 0) grp_bgn = 0;
|
||||
}
|
||||
}
|
||||
|
||||
// assert new grp_end is not > grp_max; note that this needs to be specified for when grp_key is null and not null
|
||||
int grp_max = grp.Itms__len();
|
||||
if (grp_end > grp_max)
|
||||
grp_end = grp_max;
|
||||
grp.Rng_(grp_bgn, grp_end);
|
||||
}
|
||||
}
|
||||
@@ -1,107 +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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.utls; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import org.junit.*; import gplx.core.tests.*;
|
||||
import gplx.xowa.apps.urls.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.urls.*;
|
||||
public class Xoctg_catpage_filter__tst {
|
||||
private final Xoctg_catpage_filter__fxt fxt = new Xoctg_catpage_filter__fxt();
|
||||
private Xoctg_catpage_ctg ctg;
|
||||
@Before public void init() {
|
||||
this.ctg = fxt.Make__ctg(25, 25, 25);
|
||||
}
|
||||
@Test public void Initial() {
|
||||
fxt.Exec__filter(5, "A", ctg);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__subc, 0, 5);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__page, 0, 5);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__file, 0, 5);
|
||||
}
|
||||
@Test public void Fwd__page__05() {
|
||||
fxt.Exec__filter(5, "A?pagefrom=05", ctg);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__page, 5, 10);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__subc, 0, 5);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__file, 0, 5);
|
||||
}
|
||||
@Test public void Fwd__page__10() {
|
||||
fxt.Exec__filter(5, "A?pagefrom=10", ctg);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__page, 10, 15);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__subc, 0, 5);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__file, 0, 5);
|
||||
}
|
||||
@Test public void Fwd__page__23() {
|
||||
fxt.Exec__filter(5, "A?pagefrom=23", ctg);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__page, 23, 25);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__subc, 0, 5);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__file, 0, 5);
|
||||
}
|
||||
@Test public void Fwd__full__06() {
|
||||
fxt.Exec__filter(5, "A?from=06", ctg);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__page, 6, 11);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__subc, 6, 11);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__file, 6, 11);
|
||||
}
|
||||
@Test public void Bwd__page__20() {
|
||||
fxt.Exec__filter(5, "A?pageuntil=20", ctg);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__page, 15, 20);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__subc, 0, 5);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__file, 0, 5);
|
||||
}
|
||||
@Test public void Bwd__page__2() {
|
||||
fxt.Exec__filter(5, "A?pageuntil=01", ctg);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__page, 0, 1);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__subc, 0, 5);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__file, 0, 5);
|
||||
}
|
||||
@Test public void Bwd__full__11() {
|
||||
fxt.Exec__filter(5, "A?until=11", ctg);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__page, 6, 11);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__subc, 6, 11);
|
||||
fxt.Test__cat_grp(ctg, Xoa_ctg_mgr.Tid__file, 6, 11);
|
||||
}
|
||||
}
|
||||
class Xoctg_catpage_filter__fxt {
|
||||
private Xow_url_parser url_parser;
|
||||
public Xoctg_catpage_filter__fxt() {
|
||||
Xoa_app app = Xoa_app_fxt.Make__app__edit();
|
||||
this.url_parser = app.User().Wikii().Utl__url_parser();
|
||||
}
|
||||
public Xoctg_catpage_ctg Make__ctg(int subc, int page, int file) {
|
||||
Xoctg_catpage_ctg ctg = new Xoctg_catpage_ctg(Bry_.new_a7("A"));
|
||||
Make__ctg_grp(ctg, Xoa_ctg_mgr.Tid__subc, subc);
|
||||
Make__ctg_grp(ctg, Xoa_ctg_mgr.Tid__page, page);
|
||||
Make__ctg_grp(ctg, Xoa_ctg_mgr.Tid__file, file);
|
||||
return ctg;
|
||||
}
|
||||
private void Make__ctg_grp(Xoctg_catpage_ctg ctg, byte tid, int count) {
|
||||
Xoctg_catpage_grp grp = ctg.Grp_by_tid(tid);
|
||||
for (int i = 0; i < count; ++i) {
|
||||
Xoctg_catpage_itm itm = new Xoctg_catpage_itm(i * tid, Xoa_ttl.Null, Bry_.new_a7(Int_.To_str_pad_bgn_zero(i, 2)));
|
||||
grp.Itms__add(itm);
|
||||
}
|
||||
grp.Itms__make();
|
||||
}
|
||||
public void Exec__filter(int limit, String cat_url_str, Xoctg_catpage_ctg ctg) {
|
||||
Xoctg_catpage_url cat_url = Xoctg_catpage_url_parser.Parse(url_parser.Parse(Bry_.new_a7(cat_url_str)));
|
||||
Xoctg_catpage_filter.Filter(limit, cat_url, ctg);
|
||||
}
|
||||
public void Test__cat_grp(Xoctg_catpage_ctg ctg, byte tid, int expd_bgn, int expd_end) {
|
||||
Xoctg_catpage_grp grp = ctg.Grp_by_tid(tid);
|
||||
Gftest.Eq__int(expd_bgn, grp.Bgn(), "bgn failed; tid={0}", tid);
|
||||
Gftest.Eq__int(expd_end, grp.End(), "end failed; tid={0}", tid);
|
||||
}
|
||||
}
|
||||
@@ -1,120 +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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.addons.wikis.ctgs.htmls.catpages.utls; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.wikis.*; import gplx.xowa.addons.wikis.ctgs.*; import gplx.xowa.addons.wikis.ctgs.htmls.*; import gplx.xowa.addons.wikis.ctgs.htmls.catpages.*;
|
||||
import gplx.dbs.*; import gplx.xowa.wikis.data.*; import gplx.xowa.wikis.data.tbls.*; import gplx.xowa.addons.wikis.ctgs.dbs.*;
|
||||
import gplx.xowa.addons.wikis.ctgs.htmls.catpages.doms.*;
|
||||
public class Xoctg_catpage_loader {
|
||||
private static final Object thread_lock = new Object();
|
||||
public Xoctg_catpage_ctg Load_by_ttl_or_null(Xow_wiki wiki, Xoa_ttl cat_ttl) {
|
||||
// get cat_id for cat_ttl from page_tbl
|
||||
Xow_db_mgr db_mgr = wiki.Data__core_mgr();
|
||||
Xowd_page_tbl page_tbl = db_mgr.Db__core().Tbl__page();
|
||||
Xowd_page_itm page_itm = page_tbl.Select_by_ttl_as_itm_or_null(cat_ttl);
|
||||
if (page_itm == null) {
|
||||
Gfo_usr_dlg_.Instance.Warn_many("", "", "category does not exist in page table; ttl=~{0}", cat_ttl.Full_db());
|
||||
return null;
|
||||
}
|
||||
|
||||
// get cat_link db from cat_core_tbl
|
||||
Xowd_cat_core_tbl cat_core_tbl = Xodb_cat_db_.Get_cat_core_or_fail(db_mgr);
|
||||
int cat_id = page_itm.Id();
|
||||
Xowd_category_itm cat_core_itm = cat_core_tbl.Select(cat_id);
|
||||
if (cat_core_itm == Xowd_category_itm.Null) {
|
||||
Gfo_usr_dlg_.Instance.Log_many("", "", "category does not exist in cat_core table; ttl=~{0}", cat_ttl.Full_db()); // NOTE: this is not rare as Category pages can be created as deliberately empty, or as redirects; fr.w:Catégorie:Utilisateur_hess-4; DATE:2016-09-12
|
||||
return null;
|
||||
}
|
||||
|
||||
// load itms from cat_link_db
|
||||
Xoctg_catpage_ctg rv = new Xoctg_catpage_ctg(cat_ttl.Page_txt());
|
||||
if (cat_core_itm.File_idx() == -1) // new v3: loop over all cat_link dbs
|
||||
Search_cat_core_tbls_for_cat_id(rv, wiki, db_mgr, page_tbl.Conn(), cat_core_tbl.Conn(), cat_id);
|
||||
else { // old v2: use cat_link_db
|
||||
Xow_db_file cat_link_db = db_mgr.Dbs__get_by_id_or_fail(cat_core_itm.File_idx());
|
||||
Select_by_cat_id(rv, wiki, page_tbl.Conn(), cat_core_tbl.Conn(), cat_link_db.Conn(), cat_id, Sql_for_v2(cat_id));
|
||||
}
|
||||
rv.Make_itms();
|
||||
return rv;
|
||||
}
|
||||
private static void Search_cat_core_tbls_for_cat_id(Xoctg_catpage_ctg rv, Xow_wiki wiki, Xow_db_mgr db_mgr, Db_conn page_conn, Db_conn cat_core_conn, int cat_id) {
|
||||
// loop over each db unless (a) cat_link_db; (b) core_db (if all or few)
|
||||
int len = db_mgr.Dbs__len();
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Xow_db_file db_file = db_mgr.Dbs__get_at(i);
|
||||
switch (db_file.Tid()) {
|
||||
case Xow_db_file_.Tid__cat_link: // always use cat_link db
|
||||
break;
|
||||
case Xow_db_file_.Tid__core: // only use core if all or few
|
||||
if (db_mgr.Props().Layout_text().Tid_is_lot())
|
||||
continue;
|
||||
else
|
||||
break;
|
||||
default: // else ignore all other files
|
||||
continue;
|
||||
}
|
||||
Select_by_cat_id(rv, wiki, page_conn, cat_core_conn, db_file.Conn(), cat_id, Sql_for_v3(cat_id));
|
||||
}
|
||||
}
|
||||
private static void Select_by_cat_id(Xoctg_catpage_ctg rv, Xow_wiki wiki, Db_conn page_conn, Db_conn cat_core_conn, Db_conn cat_link_conn, int cat_id, String sql) {
|
||||
// prep sql
|
||||
Db_attach_mgr attach_mgr = new Db_attach_mgr(cat_link_conn, new Db_attach_itm("page_db", page_conn), new Db_attach_itm("cat_core_db", cat_core_conn));
|
||||
sql = attach_mgr.Resolve_sql(sql);
|
||||
|
||||
// run sql and create itms based on cat_link
|
||||
Db_rdr rdr = Db_rdr_.Empty;
|
||||
synchronized (thread_lock) { // LOCK:used by multiple wrks; DATE:2016-09-12
|
||||
try {
|
||||
attach_mgr.Attach();
|
||||
rdr = cat_link_conn.Stmt_sql(sql).Exec_select__rls_auto();
|
||||
while (rdr.Move_next()) {
|
||||
Xoa_ttl page_ttl = wiki.Ttl_parse(rdr.Read_int("page_namespace"), rdr.Read_bry_by_str("page_title"));
|
||||
Xoctg_catpage_itm itm = new Xoctg_catpage_itm(rdr.Read_int("cl_from"), page_ttl, Bry_.new_u8(rdr.Read_str("cl_sortkey")));
|
||||
rv.Grp_by_tid(rdr.Read_byte("cl_type_id")).Itms__add(itm);
|
||||
}
|
||||
}
|
||||
finally {
|
||||
rdr.Rls();
|
||||
attach_mgr.Detach();
|
||||
}
|
||||
}
|
||||
}
|
||||
private static String Sql_for_v3(int cat_id) {
|
||||
return String_.Concat_lines_nl_skip_last // ANSI.Y
|
||||
( "SELECT cl.cl_from"
|
||||
, ", cl.cl_type_id"
|
||||
, ", p.page_namespace"
|
||||
, ", p.page_title"
|
||||
, ", cs.cs_key AS cl_sortkey"
|
||||
, "FROM cat_link cl"
|
||||
, " JOIN <page_db>page p ON cl.cl_from = p.page_id"
|
||||
, " JOIN <cat_core_db>cat_sort cs ON cl.cl_sortkey_id = cs.cs_id"
|
||||
, "WHERE cl.cl_to_id = " + Int_.To_str(cat_id)
|
||||
);
|
||||
}
|
||||
private static String Sql_for_v2(int cat_id) { // NOTE: main difference is cl_sortkey is on cat_link, not in cat_sort
|
||||
return String_.Concat_lines_nl_skip_last // ANSI.Y
|
||||
( "SELECT cl.cl_from"
|
||||
, ", cl.cl_type_id"
|
||||
, ", p.page_namespace"
|
||||
, ", p.page_title"
|
||||
, ", cl.cl_sortkey"
|
||||
, "FROM cat_link cl"
|
||||
, " JOIN <page_db>page p ON cl.cl_from = p.page_id"
|
||||
, "WHERE cl.cl_to_id = " + Int_.To_str(cat_id)
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -31,7 +31,7 @@ class Xoctg_pagebox_loader implements Select_in_cbk {
|
||||
int cat_id = rdr.Read_int("cat_id");
|
||||
Xoctg_pagebox_itm page = (Xoctg_pagebox_itm)hash.Get_by_id(cat_id);
|
||||
if (page == null) {// unlikely, but possible for itms to exist in cat_links, but not in cat_core; log and return;
|
||||
Gfo_usr_dlg_.Instance.Warn_many("", "", "cat_id in cat_link but not in cat_core; page=~{0} cat_id=~{0}", page_url, cat_id);
|
||||
Gfo_usr_dlg_.Instance.Warn_many("", "", "cat_id in cat_link but not in cat_core; page=~{0} cat_id=~{1}", page_url, cat_id);
|
||||
}
|
||||
page.Load_by_cat_core(rdr.Read_bool_by_byte("cat_hidden"), rdr.Read_int("cat_pages"), rdr.Read_int("cat_subcats"), rdr.Read_int("cat_files"));
|
||||
}
|
||||
|
||||
@@ -46,7 +46,7 @@ public class Xoctg_pagebox_wtr {
|
||||
Xoctg_pagebox_loader select_cbk = new Xoctg_pagebox_loader(hash, page.Url_bry_safe());
|
||||
|
||||
// get cat_db_id from page
|
||||
boolean exists = wiki.Data__core_mgr().Tbl__page().Select_by_ttl(tmp_page_itm, page.Ttl().Ns(), page.Ttl().Page_txt());
|
||||
boolean exists = wiki.Data__core_mgr().Tbl__page().Select_by_ttl(tmp_page_itm, page.Ttl().Ns(), page.Ttl().Page_db());
|
||||
int cat_db_id = tmp_page_itm.Cat_db_id();
|
||||
if (exists && cat_db_id != -1) {// note that wtxt_dbs can have 0 ctgs but will have cat_db_id == -1
|
||||
Xow_db_file cat_link_db = wiki.Data__core_mgr().Dbs__get_by_id_or_null(cat_db_id);
|
||||
|
||||
@@ -35,9 +35,9 @@ public class Xoctg_double_box implements Bfr_arg {
|
||||
|
||||
int len = ary.length;
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Xoctg_pagebox_itm ctg = ary[i];
|
||||
Xoctg_double_grp list = ctg.Hidden() ? grp_hidden : grp_normal;
|
||||
list.Itms().Itms__add(ctg);
|
||||
Xoctg_pagebox_itm itm = ary[i];
|
||||
Xoctg_double_grp list = itm.Hidden() ? grp_hidden : grp_normal;
|
||||
list.Itms().Itms__add(itm);
|
||||
}
|
||||
this.Bfr_arg__add(bfr);
|
||||
}
|
||||
|
||||
@@ -31,7 +31,7 @@ public class Xowd_html_tbl_mgr {
|
||||
byte[] content_sub = null;
|
||||
byte[] sidebar_div = null;
|
||||
db.Conn().Meta_tbl_assert(tbl);
|
||||
tbl.Upsert(page_id, Xopg_module_mgr.Tid_null, Io_stream_.Tid_raw, Xoh_hzip_dict_.Hzip__plain, display_ttl, content_sub, sidebar_div, src);
|
||||
tbl.Upsert(page_id, Xopg_module_mgr.Tid_null, Io_stream_tid_.Tid__raw, Xoh_hzip_dict_.Hzip__plain, display_ttl, content_sub, sidebar_div, src);
|
||||
|
||||
wiki.Data__core_mgr().Db__core().Tbl__page().Update__html_db_id(page_id, db.Id());
|
||||
}
|
||||
|
||||
@@ -38,8 +38,7 @@ public class Srch_search_cfg implements Gfo_invk {
|
||||
public void Args_default_str_(String v) {
|
||||
this.args_default_str = v;
|
||||
byte[] bry = Bry_.new_a7("http://x.org/a?" + v);
|
||||
Gfo_url tmp_url = new Gfo_url();
|
||||
app.User().Wikii().Utl__url_parser().Url_parser().Parse(tmp_url, bry, 0, bry.length);
|
||||
Gfo_url tmp_url = app.User().Wikii().Utl__url_parser().Url_parser().Parse(bry, 0, bry.length);
|
||||
args_default = tmp_url.Qargs();
|
||||
}
|
||||
private Srch_search_addon addon;
|
||||
|
||||
@@ -21,10 +21,17 @@ public class Xoapi_addon implements Gfo_invk {
|
||||
public void Ctor_by_app(Xoa_app app) {}
|
||||
public Xoapi_addon_search Search() {return search;} private final Xoapi_addon_search search = new Xoapi_addon_search();
|
||||
public Xoapi_addon_bldr Bldr() {return bldr;} private final Xoapi_addon_bldr bldr = new Xoapi_addon_bldr();
|
||||
public boolean Wikis__ctgs__hidden_enabled() {return wikis__ctgs__hidden_enabled;} private boolean wikis__ctgs__hidden_enabled = false;
|
||||
public Object Invk(GfsCtx ctx, int ikey, String k, GfoMsg m) {
|
||||
if (ctx.Match(k, Invk__search)) return search;
|
||||
else if (ctx.Match(k, Invk__bldr)) return bldr;
|
||||
else if (ctx.Match(k, Invk__wikis__ctgs__hidden_enabled)) return Yn.To_str(wikis__ctgs__hidden_enabled);
|
||||
else if (ctx.Match(k, Invk__wikis__ctgs__hidden_enabled_)) wikis__ctgs__hidden_enabled = m.ReadYn("v");
|
||||
else return Gfo_invk_.Rv_unhandled;
|
||||
return this;
|
||||
}
|
||||
private static final String Invk__search = "search", Invk__bldr = "bldr";
|
||||
private static final String Invk__search = "search", Invk__bldr = "bldr"
|
||||
, Invk__wikis__ctgs__hidden_enabled = "wikis__ctgs__hidden_enabled"
|
||||
, Invk__wikis__ctgs__hidden_enabled_ = "wikis__ctgs__hidden_enabled_"
|
||||
;
|
||||
}
|
||||
|
||||
@@ -20,13 +20,14 @@ import gplx.xowa.apps.apis.xowa.addons.bldrs.*;
|
||||
public class Xoapi_addon_bldr implements Gfo_invk {
|
||||
public Xoapi_central_api Central() {return central;} private final Xoapi_central_api central = new Xoapi_central_api();
|
||||
public Xoapi_sync_api Sync() {return sync;} private final Xoapi_sync_api sync = new Xoapi_sync_api();
|
||||
public boolean Wikis__ctgs__hidden_enabled() {return wikis__ctgs__hidden_enabled;} private boolean wikis__ctgs__hidden_enabled = false;
|
||||
public Object Invk(GfsCtx ctx, int ikey, String k, GfoMsg m) {
|
||||
if (ctx.Match(k, Invk__central)) return central;
|
||||
else if (ctx.Match(k, Invk__sync)) return sync;
|
||||
else return Gfo_invk_.Rv_unhandled;
|
||||
}
|
||||
private static final String
|
||||
Invk__central = "central"
|
||||
, Invk__sync = "sync"
|
||||
Invk__central = "central"
|
||||
, Invk__sync = "sync"
|
||||
;
|
||||
}
|
||||
|
||||
@@ -29,8 +29,8 @@ public class Xoapi_import implements Gfo_invk {
|
||||
public long Html_db_max() {return html_db_max;} private long html_db_max = Io_size_.To_long_by_int_mb(1500); // 3.0 GB; v2; use same as text
|
||||
public long File_db_max() {return file_db_max;} private long file_db_max = Io_size_.To_long_by_int_mb(1500); // 3.2 GB; v2
|
||||
public byte[] Ns_file_map() {return ns_file_map;} private byte[] ns_file_map = Ns_file_map__each;
|
||||
public byte Zip_tid_text() {return zip_tid_text;} private byte zip_tid_text = Io_stream_.Tid_gzip;
|
||||
public byte Zip_tid_html() {return zip_tid_html;} private byte zip_tid_html = Io_stream_.Tid_gzip;
|
||||
public byte Zip_tid_text() {return zip_tid_text;} private byte zip_tid_text = Io_stream_tid_.Tid__gzip;
|
||||
public byte Zip_tid_html() {return zip_tid_html;} private byte zip_tid_html = Io_stream_tid_.Tid__gzip;
|
||||
public boolean Hzip_enabled() {return hzip_enabled;} private boolean hzip_enabled = Bool_.Y;
|
||||
public boolean Hzip_mode_is_b256() {return hzip_mode_is_b256;} private boolean hzip_mode_is_b256 = Bool_.Y;
|
||||
public String User_name() {return user_name;} private String user_name = "anonymous";
|
||||
@@ -51,7 +51,7 @@ public class Xoapi_import implements Gfo_invk {
|
||||
: gplx.xowa.bldrs.cmds.Xob_ns_file_itm_parser.Ns_file_map__each; // DB.FEW: DATE:2016-06-07
|
||||
// return dump_file_size < layout_text_max ? Bry_.Empty : Ns_file_map__each;
|
||||
}
|
||||
public void Zip_tid_text_raw_() {zip_tid_text = Io_stream_.Tid_raw;} // TEST:
|
||||
public void Zip_tid_text_raw_() {zip_tid_text = Io_stream_tid_.Tid__raw;} // TEST:
|
||||
public Object Invk(GfsCtx ctx, int ikey, String k, GfoMsg m) {
|
||||
if (ctx.Match(k, Invk_layout_all_max)) return Io_size_.To_str_mb(layout_all_max);
|
||||
else if (ctx.Match(k, Invk_layout_all_max_)) layout_all_max = Io_size_.To_long_by_msg_mb(m, layout_all_max);
|
||||
@@ -71,11 +71,11 @@ public class Xoapi_import implements Gfo_invk {
|
||||
else if (ctx.Match(k, Invk_file_db_max_)) file_db_max = Io_size_.To_long_by_msg_mb(m, file_db_max);
|
||||
else if (ctx.Match(k, Invk_ns_file_map)) return String_.new_u8(ns_file_map);
|
||||
else if (ctx.Match(k, Invk_ns_file_map_)) ns_file_map = m.ReadBry("v");
|
||||
else if (ctx.Match(k, Invk_zip_tid_text)) return Io_stream_.To_str(zip_tid_text);
|
||||
else if (ctx.Match(k, Invk_zip_tid_text_)) zip_tid_text = Io_stream_.To_tid(m.ReadStr("v"));
|
||||
else if (ctx.Match(k, Invk_zip_tid_text)) return Io_stream_tid_.To_key(zip_tid_text);
|
||||
else if (ctx.Match(k, Invk_zip_tid_text_)) zip_tid_text = Io_stream_tid_.To_tid(m.ReadStr("v"));
|
||||
else if (ctx.Match(k, Invk_zip_tid_list)) return Options_zip_tid__list;
|
||||
else if (ctx.Match(k, Invk_zip_tid_html)) return Io_stream_.To_str(zip_tid_html);
|
||||
else if (ctx.Match(k, Invk_zip_tid_html_)) zip_tid_html = Io_stream_.To_tid(m.ReadStr("v"));
|
||||
else if (ctx.Match(k, Invk_zip_tid_html)) return Io_stream_tid_.To_key(zip_tid_html);
|
||||
else if (ctx.Match(k, Invk_zip_tid_html_)) zip_tid_html = Io_stream_tid_.To_tid(m.ReadStr("v"));
|
||||
else if (ctx.Match(k, Invk_hzip_enabled)) return Yn.To_str(hzip_enabled);
|
||||
else if (ctx.Match(k, Invk_hzip_enabled_)) hzip_enabled = m.ReadYn("v");
|
||||
else if (ctx.Match(k, Invk_hzip_mode_is_b256)) return Yn.To_str(hzip_mode_is_b256);
|
||||
@@ -86,7 +86,7 @@ public class Xoapi_import implements Gfo_invk {
|
||||
else return Gfo_invk_.Rv_unhandled;
|
||||
return this;
|
||||
}
|
||||
private static final Keyval[] Options_zip_tid__list = Keyval_.Ary(Keyval_.new_("raw", "text"), Keyval_.new_("gzip"), Keyval_.new_("bzip2"));
|
||||
private static final Keyval[] Options_zip_tid__list = Keyval_.Ary(Keyval_.new_("raw", "text"), Keyval_.new_("gzip"), Keyval_.new_("bzip2"), Keyval_.new_("xz"));
|
||||
private static final String
|
||||
Invk_layout_all_max = "layout_all_max" , Invk_layout_all_max_ = "layout_all_max_"
|
||||
, Invk_layout_text_max = "layout_text_max" , Invk_layout_text_max_ = "layout_text_max_"
|
||||
|
||||
@@ -89,7 +89,7 @@ class Http_server_wkr implements Gfo_invk {
|
||||
// client_wtr.Write_str("Expires: Sun, 17-Jan-2038 19:14:07 GMT\n");
|
||||
String mime_type = String_.new_u8(Http_file_utl.To_mime_type_by_path_as_bry(path));
|
||||
client_wtr.Write_str("Content-Type: " + mime_type + "\n\n");
|
||||
Io_stream_rdr file_stream = Io_stream_rdr_.new_by_url_(Io_url_.new_fil_(String_.new_u8(path))).Open();
|
||||
Io_stream_rdr file_stream = Io_stream_rdr_.New_by_url(Io_url_.new_fil_(String_.new_u8(path))).Open();
|
||||
client_wtr.Write_stream(file_stream);
|
||||
file_stream.Rls(); client_rdr.Rls(); socket.Rls();
|
||||
}
|
||||
|
||||
@@ -21,7 +21,7 @@ import gplx.xowa.langs.*;
|
||||
import gplx.xowa.wikis.domains.*; import gplx.xowa.wikis.xwikis.*;
|
||||
class Xoa_site_cfg_itm__interwikimap extends Xoa_site_cfg_itm__base {
|
||||
private final Bry_bfr tmp_bfr = Bry_bfr_.New();
|
||||
private final Gfo_url_parser url_parser = new Gfo_url_parser(); private final Gfo_url url = new Gfo_url();
|
||||
private final Gfo_url_parser url_parser = new Gfo_url_parser();
|
||||
public Xoa_site_cfg_itm__interwikimap() {this.Ctor(Xoa_site_cfg_loader__inet.Qarg__interwikimap);}
|
||||
@Override public void Parse_json_ary_itm(Bry_bfr bfr, Xow_wiki wiki, int i, Json_itm itm) {
|
||||
Json_nde nde = Json_nde.cast(itm);
|
||||
@@ -40,7 +40,7 @@ class Xoa_site_cfg_itm__interwikimap extends Xoa_site_cfg_itm__base {
|
||||
byte[] line = lines[i]; if (Bry_.Len_eq_0(line)) continue; // ignore blank lines
|
||||
byte[][] flds = Bry_split_.Split(line, Byte_ascii.Pipe);
|
||||
byte[] url_fmt = flds[1];
|
||||
byte[] domain_bry = Xow_xwiki_mgr.Get_domain_from_url(url_parser, url, url_fmt);
|
||||
byte[] domain_bry = Xow_xwiki_mgr.Get_domain_from_url(url_parser, url_fmt);
|
||||
wiki.Xwiki_mgr().Add_by_atrs(flds[0], domain_bry, url_fmt);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -50,7 +50,7 @@ class Xoa_url__to_str__fxt extends Xow_url_parser_fxt { private final Xoh_hr
|
||||
public void Chk_to_str_href(boolean full, String raw, String expd) {Chk_to_str_href(cur_wiki, full, raw, expd);}
|
||||
public void Chk_to_str_href(Xowe_wiki wiki, boolean full, String raw, String expd) {
|
||||
href_parser.Parse_as_url(actl_url, Bry_.new_u8(raw), wiki, Bry__page);
|
||||
this.Chk_to_str(full, expd);
|
||||
this.Test__to_str(full, expd);
|
||||
}
|
||||
private static final byte[] Bry__page = Bry_.new_a7("Page_1");
|
||||
}
|
||||
|
||||
@@ -25,12 +25,12 @@ public class Xow_url_parser {
|
||||
private final Object thread_lock = new Object();
|
||||
private final Gfo_url_encoder encoder;
|
||||
private final Bry_bfr tmp_bfr = Bry_bfr_.Reset(255);
|
||||
private final Gfo_url_parser url_parser = new Gfo_url_parser(); private final Gfo_url gfo_url = new Gfo_url();
|
||||
private final Gfo_url_parser url_parser = new Gfo_url_parser();
|
||||
private final Gfo_url_encoder gfs_encoder = Gfo_url_encoder_.New__gfs().Make();
|
||||
private final Xoa_app app; private final Xow_wiki wiki; private final byte[] domain_bry;
|
||||
private byte tmp_protocol_tid;
|
||||
private int tmp_tid;
|
||||
private byte[] tmp_raw, tmp_wiki, tmp_page, tmp_anch, tmp_protocol_bry; private Gfo_qarg_itm[] tmp_qargs;
|
||||
private byte[] tmp_raw, tmp_orig, tmp_wiki, tmp_page, tmp_anch, tmp_protocol_bry; private Gfo_qarg_itm[] tmp_qargs;
|
||||
private byte[][] tmp_segs; private int tmp_segs_len;
|
||||
private boolean tmp_protocol_is_relative, tmp_page_is_main, tmp_wiki_is_missing;
|
||||
private byte[] tmp_vnt;
|
||||
@@ -69,9 +69,10 @@ public class Xow_url_parser {
|
||||
public boolean Parse(Xoa_url rv, byte[] src, int bgn, int end) {
|
||||
synchronized (thread_lock) {
|
||||
if (end - bgn == 0) {Init_tmp_vars(Gfo_url.Empty); Make(rv); return false;}
|
||||
src = encoder.Decode(src, bgn, end); // NOTE: must decode any url-encoded parameters
|
||||
int src_len = src.length;
|
||||
url_parser.Parse(gfo_url, src, 0, src_len); // parse to plain gfo_url
|
||||
tmp_orig = (bgn == 0 && end == src.length) ? src : Bry_.Mid(src, bgn, end);
|
||||
// src = encoder.Decode(src, bgn, end); // NOTE: must decode any url-encoded parameters; TOMBSTONE:do not auto-decode DATE:2016-10-10
|
||||
int src_len = end - bgn;
|
||||
Gfo_url gfo_url = url_parser.Parse(src, bgn, end); // parse to plain gfo_url
|
||||
Init_tmp_vars(gfo_url);
|
||||
if (src[0] == Byte_ascii.Hash) // src is anch; EX: #A
|
||||
Bld_anch();
|
||||
@@ -134,7 +135,7 @@ public class Xow_url_parser {
|
||||
}
|
||||
private Xoa_url Make(Xoa_url rv) {
|
||||
rv.Ctor
|
||||
( tmp_tid, tmp_raw, tmp_protocol_tid, tmp_protocol_bry, tmp_protocol_is_relative
|
||||
( tmp_tid, tmp_orig, tmp_raw, tmp_protocol_tid, tmp_protocol_bry, tmp_protocol_is_relative
|
||||
, tmp_wiki, tmp_page, tmp_qargs, tmp_anch
|
||||
, tmp_segs, tmp_vnt, tmp_wiki_is_missing, Bry_.Eq(tmp_wiki, wiki.Domain_bry()), tmp_page_is_main);
|
||||
return rv;
|
||||
@@ -264,9 +265,7 @@ public class Xow_url_parser {
|
||||
int qargs_len = tmp_qargs.length;
|
||||
for (int i = 0; i < qargs_len; ++i) {
|
||||
Gfo_qarg_itm qarg = tmp_qargs[i];
|
||||
if ( Bry_.Eq(qarg.Key_bry(), Qarg__title)
|
||||
&& qarg.Val_bry() != null // HACK: handle "bad-urls" from xml-encoded entities where page is null b/c = is encoded as =; http://en.wikipedia.org/w/index.php?action=edit&preload=Template:Afd2+starter&editintro=Template:Afd3+starter&title=Wikipedia:Articles+for+deletion/Template standardisation/demometa DATE:2015-08-02
|
||||
)
|
||||
if (Bry_.Eq(qarg.Key_bry(), Qarg__title))
|
||||
tmp_page = qarg.Val_bry(); // handle /w/index.php?title=Earth
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,23 +20,23 @@ import org.junit.*;
|
||||
public class Xow_url_parser__proto_tst {
|
||||
private final Xow_url_parser_fxt tstr = new Xow_url_parser_fxt();
|
||||
@Test public void Relative() {
|
||||
tstr.Run_parse("//en.wikipedia.org/wiki/A").Chk_wiki("en.wikipedia.org").Chk_page("A");
|
||||
tstr.Exec__parse("//en.wikipedia.org/wiki/A").Test__wiki("en.wikipedia.org").Test__page("A");
|
||||
}
|
||||
@Test public void Http__basic() {
|
||||
tstr.Run_parse("http://en.wikipedia.org/wiki/A").Chk_wiki("en.wikipedia.org").Chk_page("A");
|
||||
tstr.Exec__parse("http://en.wikipedia.org/wiki/A").Test__wiki("en.wikipedia.org").Test__page("A");
|
||||
}
|
||||
@Test public void Upload__basic() {
|
||||
tstr.Prep_add_xwiki_to_user("commons.wikimedia.org"); // NOTE: need to add xwiki to be able to resolve "/commons/"
|
||||
tstr.Run_parse("http://upload.wikimedia.org/wikipedia/commons/a/ab/C.svg").Chk_wiki("commons.wikimedia.org").Chk_page("File:C.svg"); // orig
|
||||
tstr.Run_parse("http://upload.wikimedia.org/wikipedia/commons/thumb/7/70/A.png/220px-A.png").Chk_wiki("commons.wikimedia.org").Chk_page("File:A.png"); // thum
|
||||
tstr.Exec__parse("http://upload.wikimedia.org/wikipedia/commons/a/ab/C.svg").Test__wiki("commons.wikimedia.org").Test__page("File:C.svg"); // orig
|
||||
tstr.Exec__parse("http://upload.wikimedia.org/wikipedia/commons/thumb/7/70/A.png/220px-A.png").Test__wiki("commons.wikimedia.org").Test__page("File:A.png"); // thum
|
||||
}
|
||||
@Test public void File__basic() {
|
||||
tstr.Run_parse("file:///C:/a/b/c").Chk_tid(Xoa_url_.Tid_file);
|
||||
tstr.Exec__parse("file:///C:/a/b/c").Test__tid(Xoa_url_.Tid_file);
|
||||
}
|
||||
@Test public void Ftp__basic() {
|
||||
tstr.Run_parse("ftp://en.wikipedia.org/wiki/A").Chk_tid(Xoa_url_.Tid_inet);
|
||||
tstr.Exec__parse("ftp://en.wikipedia.org/wiki/A").Test__tid(Xoa_url_.Tid_inet);
|
||||
}
|
||||
@Test public void Extended() {
|
||||
tstr.Run_parse("http://en.wikipedia.org/w/index.php?A=B").Chk_wiki("en.wikipedia.org").Chk_page("index.php").Chk_qargs("?A=B").Chk_anch(null);
|
||||
tstr.Exec__parse("http://en.wikipedia.org/w/index.php?A=B").Test__wiki("en.wikipedia.org").Test__page("index.php").Test__qargs("?A=B").Test__anch(null);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,68 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.apps.urls; import gplx.*; import gplx.xowa.*; import gplx.xowa.apps.*;
|
||||
import org.junit.*;
|
||||
public class Xow_url_parser__qarg__tst {
|
||||
private final Xow_url_parser_fxt fxt = new Xow_url_parser_fxt();
|
||||
@Test public void Redirect() {
|
||||
fxt.Exec__parse("A?redirect=no").Test__wiki("en.wikipedia.org").Test__page("A").Test__qargs("?redirect=no");
|
||||
}
|
||||
@Test public void Action_is_edit() {
|
||||
fxt.Exec__parse("A?action=edit").Test__wiki("en.wikipedia.org").Test__page("A").Test__action_is_edit_y();
|
||||
}
|
||||
@Test public void Assert_state_cleared() { // PURPOSE.fix: action_is_edit (et. al.) was not being cleared on parse even though Xoa_url reused; DATE:20121231
|
||||
fxt.Exec__parse("A?action=edit") .Test__action_is_edit_y();
|
||||
fxt.Exec__parse_reuse("B") .Test__action_is_edit_n();
|
||||
}
|
||||
@Test public void Query_arg() { // PURPOSE.fix: query args were not printing out
|
||||
fxt.Exec__parse("en.wikipedia.org/wiki/Special:Search/Earth?fulltext=yes").Test__build_str_is_same();
|
||||
}
|
||||
@Test public void Dupe_key() {
|
||||
fxt.Exec__parse("A?B=C1&B=C2").Test__page("A").Test__qargs("?B=C1&B=C2");
|
||||
}
|
||||
@Test public void Question_is_eos() {
|
||||
fxt.Exec__parse("A?").Test__wiki("en.wikipedia.org").Test__page("A?").Test__qargs("");
|
||||
}
|
||||
@Test public void Question_is_page() {
|
||||
fxt.Exec__parse("A?B").Test__wiki("en.wikipedia.org").Test__page("A?B").Test__qargs("");
|
||||
}
|
||||
@Test public void Question_is_anchor() {
|
||||
fxt.Exec__parse("A#b?c").Test__wiki("en.wikipedia.org").Test__page("A").Test__anch("b.3Fc");
|
||||
}
|
||||
@Test public void Title_remove_w() { // PURPOSE: fix /w/ showing up as seg; DATE:2014-05-30
|
||||
fxt.Exec__parse("http://en.wikipedia.org/w/index.php?title=A").Test__wiki("en.wikipedia.org").Test__page("A");
|
||||
}
|
||||
@Test public void Ctg() {
|
||||
fxt.Exec__parse("Category:A?pagefrom=A#mw-pages").Test__page("Category:A").Test__qargs("?pagefrom=A").Test__anch("mw-pages");
|
||||
}
|
||||
@Test public void Anch() {
|
||||
fxt.Exec__parse("A?k1=v1#anch");
|
||||
fxt.Test__page("A");
|
||||
fxt.Test__anch("anch");
|
||||
fxt.Test__qargs("?k1=v1");
|
||||
fxt.Test__to_str("en.wikipedia.org/wiki/A?k1=v1#anch");
|
||||
}
|
||||
// DELETED: search should not depend on url-decoded entities; should be "Special:Search/Moon?fulltext=y&xowa_page_index=1" DATE:2016-10-10
|
||||
// @Test public void Search() {
|
||||
// fxt.Exec__parse("Special:Search/Moon%3Ffulltext%3Dy%26xowa_page_index%3D1").Test__page("Special:Search/Moon").Test__qargs("?fulltext=y&xowa_page_index=1");
|
||||
//}
|
||||
// DELETED: this is wrong as url should not handle html_entities like = instead # should strictly designate anch_href; DATE:2016-10-10
|
||||
// @Test public void Encoded() {
|
||||
// fxt.Exec__parse("en.wikipedia.org/wiki/A?action=edit&preload=B").Test__wiki("en.wikipedia.org").Test__page("A").Test__qargs("?action==edit=&preload=&=").Test__anch("61.3BB"); // NOTE: this is wrong; fix later
|
||||
// }
|
||||
}
|
||||
@@ -1,59 +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 <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.apps.urls; import gplx.*; import gplx.xowa.*; import gplx.xowa.apps.*;
|
||||
import org.junit.*;
|
||||
public class Xow_url_parser__qarg_tst {
|
||||
private final Xow_url_parser_fxt tstr = new Xow_url_parser_fxt();
|
||||
@Test public void Redirect() {
|
||||
tstr.Run_parse("A?redirect=no").Chk_wiki("en.wikipedia.org").Chk_page("A").Chk_qargs("?redirect=no");
|
||||
}
|
||||
@Test public void Action_is_edit() {
|
||||
tstr.Run_parse("A?action=edit").Chk_wiki("en.wikipedia.org").Chk_page("A").Chk_action_is_edit_y();
|
||||
}
|
||||
@Test public void Assert_state_cleared() { // PURPOSE.fix: action_is_edit (et. al.) was not being cleared on parse even though Xoa_url reused; DATE:20121231
|
||||
tstr.Run_parse("A?action=edit") .Chk_action_is_edit_y();
|
||||
tstr.Run_parse_reuse("B") .Chk_action_is_edit_n();
|
||||
}
|
||||
@Test public void Query_arg() { // PURPOSE.fix: query args were not printing out
|
||||
tstr.Run_parse("en.wikipedia.org/wiki/Special:Search/Earth?fulltext=yes").Chk_build_str_is_same();
|
||||
}
|
||||
@Test public void Dupe_key() {
|
||||
tstr.Run_parse("A?B=C1&B=C2").Chk_page("A").Chk_qargs("?B=C1&B=C2");
|
||||
}
|
||||
@Test public void Question_is_eos() {
|
||||
tstr.Run_parse("A?").Chk_wiki("en.wikipedia.org").Chk_page("A?").Chk_qargs("");
|
||||
}
|
||||
@Test public void Question_is_page() {
|
||||
tstr.Run_parse("A?B").Chk_wiki("en.wikipedia.org").Chk_page("A?B").Chk_qargs("");
|
||||
}
|
||||
@Test public void Question_is_anchor() {
|
||||
tstr.Run_parse("A#b?c").Chk_wiki("en.wikipedia.org").Chk_page("A").Chk_anch("b.3Fc");
|
||||
}
|
||||
@Test public void Title_remove_w() { // PURPOSE: fix /w/ showing up as seg; DATE:2014-05-30
|
||||
tstr.Run_parse("http://en.wikipedia.org/w/index.php?title=A").Chk_wiki("en.wikipedia.org").Chk_page("A");
|
||||
}
|
||||
@Test public void Search() {
|
||||
tstr.Run_parse("Special:Search/Moon%3Ffulltext%3Dy%26xowa_page_index%3D1").Chk_page("Special:Search/Moon").Chk_qargs("?fulltext=y&xowa_page_index=1");
|
||||
}
|
||||
@Test public void Ctg() {
|
||||
tstr.Run_parse("Category:A?pagefrom=A#mw-pages").Chk_page("Category:A").Chk_qargs("?pagefrom=A").Chk_anch("mw-pages");
|
||||
}
|
||||
@Test public void Encoded() {
|
||||
tstr.Run_parse("en.wikipedia.org/wiki/A?action=edit&preload=B").Chk_wiki("en.wikipedia.org").Chk_page("A").Chk_qargs("?action==edit=&preload=&=").Chk_anch("61.3BB"); // NOTE: this is wrong; fix later
|
||||
}
|
||||
}
|
||||
@@ -20,37 +20,37 @@ import org.junit.*;
|
||||
public class Xow_url_parser__ttl_tst {
|
||||
private final Xow_url_parser_fxt tstr = new Xow_url_parser_fxt();
|
||||
@Test public void Name() {
|
||||
tstr.Run_parse("A").Chk_wiki("en.wikipedia.org").Chk_page("A");
|
||||
tstr.Exec__parse("A").Test__wiki("en.wikipedia.org").Test__page("A");
|
||||
}
|
||||
@Test public void Sub_1() {
|
||||
tstr.Run_parse("A/b").Chk_wiki("en.wikipedia.org").Chk_page("A/b");
|
||||
tstr.Exec__parse("A/b").Test__wiki("en.wikipedia.org").Test__page("A/b");
|
||||
}
|
||||
@Test public void Sub_2() {
|
||||
tstr.Run_parse("A/b/c").Chk_wiki("en.wikipedia.org").Chk_page("A/b/c");
|
||||
tstr.Exec__parse("A/b/c").Test__wiki("en.wikipedia.org").Test__page("A/b/c");
|
||||
}
|
||||
@Test public void Anch() {
|
||||
tstr.Run_parse("A#b").Chk_wiki("en.wikipedia.org").Chk_page("A").Chk_anch("b");
|
||||
tstr.Exec__parse("A#b").Test__wiki("en.wikipedia.org").Test__page("A").Test__anch("b");
|
||||
}
|
||||
@Test public void Anch_w_slash() { // PURPOSE: A/b#c/d was not parsing correctly; PAGE:en.w:Enlightenment_Spain#Enlightened_despotism_.281759%E2%80%931788.29
|
||||
tstr.Run_parse("A/b#c/d").Chk_page("A/b").Chk_anch("c.2Fd");
|
||||
tstr.Exec__parse("A/b#c/d").Test__page("A/b").Test__anch("c.2Fd");
|
||||
}
|
||||
@Test public void Ns_category() {
|
||||
tstr.Run_parse("Category:A").Chk_wiki("en.wikipedia.org").Chk_page("Category:A");
|
||||
tstr.Exec__parse("Category:A").Test__wiki("en.wikipedia.org").Test__page("Category:A");
|
||||
}
|
||||
@Test public void Main_page__basic() {
|
||||
tstr.Run_parse("en.wikipedia.org") .Chk_wiki("en.wikipedia.org").Chk_page_is_main_y();
|
||||
tstr.Run_parse("en.wikipedia.org/") .Chk_wiki("en.wikipedia.org").Chk_page_is_main_y();
|
||||
tstr.Run_parse("en.wikipedia.org/wiki") .Chk_wiki("en.wikipedia.org").Chk_page_is_main_y();
|
||||
tstr.Run_parse("en.wikipedia.org/wiki/") .Chk_wiki("en.wikipedia.org").Chk_page_is_main_y();
|
||||
tstr.Run_parse("en.wikipedia.org/wiki/A") .Chk_wiki("en.wikipedia.org").Chk_page_is_main_n();
|
||||
tstr.Exec__parse("en.wikipedia.org") .Test__wiki("en.wikipedia.org").Test__page_is_main_y();
|
||||
tstr.Exec__parse("en.wikipedia.org/") .Test__wiki("en.wikipedia.org").Test__page_is_main_y();
|
||||
tstr.Exec__parse("en.wikipedia.org/wiki") .Test__wiki("en.wikipedia.org").Test__page_is_main_y();
|
||||
tstr.Exec__parse("en.wikipedia.org/wiki/") .Test__wiki("en.wikipedia.org").Test__page_is_main_y();
|
||||
tstr.Exec__parse("en.wikipedia.org/wiki/A") .Test__wiki("en.wikipedia.org").Test__page_is_main_n();
|
||||
}
|
||||
@Test public void Ns_file__basic() {// PURPOSE: "File:A" should not be mistaken for "file:///" ns
|
||||
tstr.Run_parse("File:A").Chk_wiki("en.wikipedia.org").Chk_page("File:A");
|
||||
tstr.Exec__parse("File:A").Test__wiki("en.wikipedia.org").Test__page("File:A");
|
||||
}
|
||||
@Test public void Ns_file__nested() {// PURPOSE: handle fictitious "File:A/B/C.png"
|
||||
tstr.Run_parse("File:A/B/C.png").Chk_wiki("en.wikipedia.org").Chk_page("File:A/B/C.png"); // should not be C.png b/c of Gfo_url_parser_old
|
||||
tstr.Exec__parse("File:A/B/C.png").Test__wiki("en.wikipedia.org").Test__page("File:A/B/C.png"); // should not be C.png b/c of Gfo_url_parser_old
|
||||
}
|
||||
@Test public void Anch__basic() {// DATE:2015-07-26
|
||||
tstr.Run_parse("#A").Chk_tid(Xoa_url_.Tid_anch).Chk_wiki_is_missing(true).Chk_page("").Chk_anch("A");
|
||||
tstr.Exec__parse("#A").Test__tid(Xoa_url_.Tid_anch).Test__wiki_is_missing(true).Test__page("").Test__anch("A");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,49 +20,49 @@ import org.junit.*;
|
||||
public class Xow_url_parser__url_bar_tst {
|
||||
private final Xow_url_parser_fxt tstr = new Xow_url_parser_fxt();
|
||||
@Test public void Basic() {
|
||||
tstr.Run_parse_from_url_bar("Page_1").Chk_to_str("en.wikipedia.org/wiki/Page_1"); // basic
|
||||
tstr.Exec__parse_from_url_bar("Page_1").Test__to_str("en.wikipedia.org/wiki/Page_1"); // basic
|
||||
}
|
||||
@Test public void Lang() {
|
||||
tstr.Prep_add_xwiki_to_user("uk", "uk.wikipedia.org");
|
||||
tstr.Run_parse_from_url_bar("uk").Chk_to_str("en.wikipedia.org/wiki/Uk"); // lang-like page (uk=Ukraine) should not try to open wiki; DATE:2014-02-07
|
||||
tstr.Exec__parse_from_url_bar("uk").Test__to_str("en.wikipedia.org/wiki/Uk"); // lang-like page (uk=Ukraine) should not try to open wiki; DATE:2014-02-07
|
||||
}
|
||||
@Test public void Lang_like() {
|
||||
tstr.Prep_add_xwiki_to_user("uk", "uk.wikipedia.org", "http://~{1}.wikipedia.org"); // NOTE: fmt needed for Type_is_lang
|
||||
tstr.Run_parse_from_url_bar("uk/A").Chk_to_str("en.wikipedia.org/wiki/Uk/A"); // uk/A should not try be interpreted as wiki="uk" page="A"; DATE:2014-04-26
|
||||
tstr.Exec__parse_from_url_bar("uk/A").Test__to_str("en.wikipedia.org/wiki/Uk/A"); // uk/A should not try be interpreted as wiki="uk" page="A"; DATE:2014-04-26
|
||||
}
|
||||
@Test public void Macro() {
|
||||
tstr.Prep_add_xwiki_to_user("fr.wikisource.org");
|
||||
tstr.Run_parse_from_url_bar("fr.s:Auteur:Shakespeare").Chk_to_str("fr.wikisource.org/wiki/Auteur:Shakespeare"); // url_macros
|
||||
tstr.Exec__parse_from_url_bar("fr.s:Auteur:Shakespeare").Test__to_str("fr.wikisource.org/wiki/Auteur:Shakespeare"); // url_macros
|
||||
}
|
||||
@Test public void Main_page__home() {
|
||||
tstr.Run_parse_from_url_bar("home").Chk_to_str("en.wikipedia.org/wiki/Home"); // home should go to current wiki's home; DATE:2014-02-09
|
||||
tstr.Run_parse_from_url_bar("home/wiki/Main_Page").Chk_to_str("home/wiki/Main_Page"); // home Main_Page should go to home; DATE:2014-02-09
|
||||
tstr.Exec__parse_from_url_bar("home").Test__to_str("en.wikipedia.org/wiki/Home"); // home should go to current wiki's home; DATE:2014-02-09
|
||||
tstr.Exec__parse_from_url_bar("home/wiki/Main_Page").Test__to_str("home/wiki/Main_Page"); // home Main_Page should go to home; DATE:2014-02-09
|
||||
}
|
||||
@Test public void Main_page__zhw() {
|
||||
Xowe_wiki zh_wiki = tstr.Prep_create_wiki("zh.wikipedia.org");
|
||||
zh_wiki.Props().Main_page_(Bry_.new_a7("Zh_Main_Page"));
|
||||
tstr.Run_parse_from_url_bar("zh.w:Main_Page") .Chk_page_is_main_n().Chk_to_str("zh.wikipedia.org/wiki/Main_Page");
|
||||
tstr.Run_parse_from_url_bar("zh.w:") .Chk_page_is_main_y().Chk_to_str("zh.wikipedia.org/wiki/Zh_Main_Page");
|
||||
tstr.Run_parse_from_url_bar("en.w:") .Chk_page_is_main_y().Chk_to_str("en.wikipedia.org/wiki/Main_Page"); // old bug: still stuck at zh main page due to reused objects
|
||||
tstr.Exec__parse_from_url_bar("zh.w:Main_Page") .Test__page_is_main_n().Test__to_str("zh.wikipedia.org/wiki/Main_Page");
|
||||
tstr.Exec__parse_from_url_bar("zh.w:") .Test__page_is_main_y().Test__to_str("zh.wikipedia.org/wiki/Zh_Main_Page");
|
||||
tstr.Exec__parse_from_url_bar("en.w:") .Test__page_is_main_y().Test__to_str("en.wikipedia.org/wiki/Main_Page"); // old bug: still stuck at zh main page due to reused objects
|
||||
}
|
||||
@Test public void Mobile() { // PURPOSE: handle mobile links; DATE:2014-05-03
|
||||
tstr.Run_parse_from_url_bar("en.m.wikipedia.org/wiki/A" ).Chk_to_str("en.wikipedia.org/wiki/A"); // basic
|
||||
tstr.Run_parse_from_url_bar("en.M.wikipedia.org/wiki/A" ).Chk_to_str("en.wikipedia.org/wiki/A"); // upper
|
||||
tstr.Run_parse_from_url_bar("A" ).Chk_to_str("en.wikipedia.org/wiki/A"); // bounds-check: 0
|
||||
tstr.Run_parse_from_url_bar("A." ).Chk_to_str("en.wikipedia.org/wiki/A."); // bounds-check: 1
|
||||
tstr.Run_parse_from_url_bar("A.b" ).Chk_to_str("en.wikipedia.org/wiki/A.b"); // bounds-check: 2
|
||||
tstr.Run_parse_from_url_bar("A.b.m." ).Chk_to_str("en.wikipedia.org/wiki/A.b.m."); // false-match
|
||||
tstr.Run_parse_from_url_bar("en.x.wikipedia.org/wiki/A" ).Chk_to_str("en.wikipedia.org/wiki/En.x.wikipedia.org/wiki/A"); // fail
|
||||
tstr.Exec__parse_from_url_bar("en.m.wikipedia.org/wiki/A" ).Test__to_str("en.wikipedia.org/wiki/A"); // basic
|
||||
tstr.Exec__parse_from_url_bar("en.M.wikipedia.org/wiki/A" ).Test__to_str("en.wikipedia.org/wiki/A"); // upper
|
||||
tstr.Exec__parse_from_url_bar("A" ).Test__to_str("en.wikipedia.org/wiki/A"); // bounds-check: 0
|
||||
tstr.Exec__parse_from_url_bar("A." ).Test__to_str("en.wikipedia.org/wiki/A."); // bounds-check: 1
|
||||
tstr.Exec__parse_from_url_bar("A.b" ).Test__to_str("en.wikipedia.org/wiki/A.b"); // bounds-check: 2
|
||||
tstr.Exec__parse_from_url_bar("A.b.m." ).Test__to_str("en.wikipedia.org/wiki/A.b.m."); // false-match
|
||||
tstr.Exec__parse_from_url_bar("en.x.wikipedia.org/wiki/A" ).Test__to_str("en.wikipedia.org/wiki/En.x.wikipedia.org/wiki/A"); // fail
|
||||
}
|
||||
@Test public void Missing_page() {
|
||||
tstr.Run_parse_from_url_bar("http://a.org").Chk_is_null(); // unknown wiki; return null;
|
||||
tstr.Run_parse_from_url_bar("http://en.wikipedia.org").Chk_to_str("en.wikipedia.org/wiki/Main_Page"); // known wiki; return Main_Page
|
||||
tstr.Exec__parse_from_url_bar("http://a.org").Test__is_null(); // unknown wiki; return null;
|
||||
tstr.Exec__parse_from_url_bar("http://en.wikipedia.org").Test__to_str("en.wikipedia.org/wiki/Main_Page"); // known wiki; return Main_Page
|
||||
}
|
||||
@Test public void Invalid_names() {
|
||||
tstr.Run_parse_from_url_bar("http://a/b/c").Chk_is_null(); // unknown url
|
||||
tstr.Run_parse_from_url_bar("war").Chk_to_str("en.wikipedia.org/wiki/War"); // word looks like lang, but is actually page; default to current
|
||||
tstr.Exec__parse_from_url_bar("http://a/b/c").Test__is_null(); // unknown url
|
||||
tstr.Exec__parse_from_url_bar("war").Test__to_str("en.wikipedia.org/wiki/War"); // word looks like lang, but is actually page; default to current
|
||||
}
|
||||
@Test public void Proper_case() {
|
||||
tstr.Run_parse_from_url_bar("a" ).Chk_to_str("en.wikipedia.org/wiki/A"); // "a" -> "A" x> "a"
|
||||
tstr.Exec__parse_from_url_bar("a" ).Test__to_str("en.wikipedia.org/wiki/A"); // "a" -> "A" x> "a"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,22 +20,22 @@ import org.junit.*;
|
||||
public class Xow_url_parser__wiki_tst {
|
||||
private final Xow_url_parser_fxt tstr = new Xow_url_parser_fxt();
|
||||
@Test public void Basic() {
|
||||
tstr.Run_parse("en.wikipedia.org/wiki/A").Chk_tid(Xoa_url_.Tid_page).Chk_wiki("en.wikipedia.org").Chk_page("A");
|
||||
tstr.Exec__parse("en.wikipedia.org/wiki/A").Test__tid(Xoa_url_.Tid_page).Test__wiki("en.wikipedia.org").Test__page("A");
|
||||
}
|
||||
@Test public void No_wiki() { // PURPOSE: no "/wiki/"
|
||||
tstr.Run_parse("en.wikipedia.org/A").Chk_wiki("en.wikipedia.org").Chk_page("A");
|
||||
tstr.Exec__parse("en.wikipedia.org/A").Test__wiki("en.wikipedia.org").Test__page("A");
|
||||
}
|
||||
@Test public void Nested() {
|
||||
tstr.Run_parse("en.wikipedia.org/wiki/A/b").Chk_wiki("en.wikipedia.org").Chk_page("A/b");
|
||||
tstr.Exec__parse("en.wikipedia.org/wiki/A/b").Test__wiki("en.wikipedia.org").Test__page("A/b");
|
||||
}
|
||||
@Test public void Slash() {
|
||||
tstr.Run_parse("en.wikipedia.org/wiki//A").Chk_wiki("en.wikipedia.org").Chk_page("/A");
|
||||
tstr.Run_parse("en.wikipedia.org/wiki/A//b").Chk_wiki("en.wikipedia.org").Chk_page("A//b");
|
||||
tstr.Run_parse("en.wikipedia.org/wiki///A").Chk_wiki("en.wikipedia.org").Chk_page("//A");
|
||||
tstr.Exec__parse("en.wikipedia.org/wiki//A").Test__wiki("en.wikipedia.org").Test__page("/A");
|
||||
tstr.Exec__parse("en.wikipedia.org/wiki/A//b").Test__wiki("en.wikipedia.org").Test__page("A//b");
|
||||
tstr.Exec__parse("en.wikipedia.org/wiki///A").Test__wiki("en.wikipedia.org").Test__page("//A");
|
||||
}
|
||||
@Test public void Vnt() {
|
||||
Xowe_wiki wiki = tstr.Wiki();
|
||||
gplx.xowa.langs.vnts.Xol_vnt_regy_fxt.Init__vnt_mgr(wiki.Lang().Vnt_mgr(), 0, String_.Ary("zh-hans", "zh-hant"));
|
||||
tstr.Run_parse("en.wikipedia.org/zh-hans/A").Chk_wiki("en.wikipedia.org").Chk_page("A").Chk_vnt("zh-hans");
|
||||
tstr.Exec__parse("en.wikipedia.org/zh-hans/A").Test__wiki("en.wikipedia.org").Test__page("A").Test__vnt("zh-hans");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,12 +20,12 @@ import org.junit.*;
|
||||
public class Xow_url_parser__xcmd_tst {
|
||||
private final Xow_url_parser_fxt tstr = new Xow_url_parser_fxt();
|
||||
@Test public void Basic() {
|
||||
tstr.Run_parse("xowa-cmd:xowa.app.version").Chk_tid(Xoa_url_.Tid_xcmd).Chk_page("xowa.app.version");
|
||||
tstr.Exec__parse("xowa-cmd:xowa.app.version").Test__tid(Xoa_url_.Tid_xcmd).Test__page("xowa.app.version");
|
||||
}
|
||||
@Test public void Encoded() {
|
||||
tstr.Run_parse("xowa-cmd:a%22b*c").Chk_tid(Xoa_url_.Tid_xcmd).Chk_page("a\"b*c");
|
||||
tstr.Exec__parse("xowa-cmd:a%22b*c").Test__tid(Xoa_url_.Tid_xcmd).Test__page("a\"b*c");
|
||||
}
|
||||
@Test public void Ignore_anchor_and_qargs() {
|
||||
tstr.Run_parse("xowa-cmd:a/b/c?d=e#f").Chk_tid(Xoa_url_.Tid_xcmd).Chk_page("a/b/c?d=e#f");
|
||||
tstr.Exec__parse("xowa-cmd:a/b/c?d=e#f").Test__tid(Xoa_url_.Tid_xcmd).Test__page("a/b/c?d=e#f");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -21,60 +21,60 @@ public class Xow_url_parser__xwiki_tst {
|
||||
private final Xow_url_parser_fxt tstr = new Xow_url_parser_fxt();
|
||||
@Test public void Commons() { // PURPOSE: "C" was being picked up as an xwiki to commons; PAGE:no.b:C/Variabler; DATE:2014-10-14
|
||||
tstr.Prep_add_xwiki_to_user("c", "commons.wikimedia.org"); // add alias of "c"
|
||||
tstr.Run_parse("C/D").Chk_tid(Xoa_url_.Tid_page).Chk_wiki("en.wikipedia.org").Chk_page("C/D"); // should use current wiki (enwiki), not xwiki to commons; also, page should be "C/D", not "D"
|
||||
tstr.Exec__parse("C/D").Test__tid(Xoa_url_.Tid_page).Test__wiki("en.wikipedia.org").Test__page("C/D"); // should use current wiki (enwiki), not xwiki to commons; also, page should be "C/D", not "D"
|
||||
}
|
||||
@Test public void Parse_lang() {
|
||||
tstr.Prep_add_xwiki_to_wiki("fr", "fr.wikipedia.org", "http://fr.wikipedia.org/~{0}");
|
||||
tstr.Run_parse("http://en.wikipedia.org/wiki/fr:A").Chk_tid(Xoa_url_.Tid_page).Chk_wiki("fr.wikipedia.org").Chk_page("A");
|
||||
tstr.Exec__parse("http://en.wikipedia.org/wiki/fr:A").Test__tid(Xoa_url_.Tid_page).Test__wiki("fr.wikipedia.org").Test__page("A");
|
||||
}
|
||||
@Test public void Alias_wiki() {
|
||||
tstr.Prep_add_xwiki_to_wiki("s", "en.wikisource.org");
|
||||
tstr.Run_parse("s:A/b/c").Chk_wiki("en.wikisource.org").Chk_page("A/b/c");
|
||||
tstr.Exec__parse("s:A/b/c").Test__wiki("en.wikisource.org").Test__page("A/b/c");
|
||||
}
|
||||
@Test public void Xwiki_no_segs() { // PURPOSE: handle xwiki without full url; EX: "commons:Commons:Media_of_the_day"; DATE:2014-02-19
|
||||
tstr.Prep_add_xwiki_to_wiki("s", "en.wikisource.org");
|
||||
tstr.Run_parse("s:Project:A").Chk_wiki("en.wikisource.org").Chk_page("Project:A");
|
||||
tstr.Exec__parse("s:Project:A").Test__wiki("en.wikisource.org").Test__page("Project:A");
|
||||
}
|
||||
@Test public void Domain_only() {
|
||||
tstr.Prep_add_xwiki_to_user("fr.wikipedia.org");
|
||||
tstr.Run_parse("fr.wikipedia.org").Chk_wiki("fr.wikipedia.org").Chk_page("");
|
||||
tstr.Exec__parse("fr.wikipedia.org").Test__wiki("fr.wikipedia.org").Test__page("");
|
||||
}
|
||||
@Test public void Domain_and_wiki() {
|
||||
tstr.Prep_add_xwiki_to_user("fr.wikipedia.org");
|
||||
tstr.Run_parse("fr.wikipedia.org/wiki").Chk_wiki("fr.wikipedia.org").Chk_page("");
|
||||
tstr.Exec__parse("fr.wikipedia.org/wiki").Test__wiki("fr.wikipedia.org").Test__page("");
|
||||
}
|
||||
@Test public void Domain_and_wiki_w_http() {
|
||||
tstr.Prep_add_xwiki_to_user("fr.wikipedia.org");
|
||||
tstr.Run_parse("http://fr.wikipedia.org/wiki").Chk_wiki("fr.wikipedia.org").Chk_page("");
|
||||
tstr.Exec__parse("http://fr.wikipedia.org/wiki").Test__wiki("fr.wikipedia.org").Test__page("");
|
||||
}
|
||||
@Test public void Namespace_in_different_wiki() { // PURPOSE.fix: namespaced titles would default to default_wiki instead of current_wiki
|
||||
Xowe_wiki en_s = tstr.Prep_create_wiki("en.wikisource.org");
|
||||
tstr.Run_parse(en_s, "Category:A").Chk_wiki("en.wikisource.org").Chk_page("Category:A");
|
||||
tstr.Exec__parse(en_s, "Category:A").Test__wiki("en.wikisource.org").Test__page("Category:A");
|
||||
}
|
||||
@Test public void Case_sensitive() {
|
||||
// tstr.Run_parse("en.wikipedia.org/wiki/a").Chk_wiki("en.wikipedia.org").Chk_page("A");
|
||||
// tstr.Exec__parse("en.wikipedia.org/wiki/a").Test__wiki("en.wikipedia.org").Test__page("A");
|
||||
Xowe_wiki en_d = tstr.Prep_create_wiki("en.wiktionary.org");
|
||||
Xow_ns_mgr ns_mgr = en_d.Ns_mgr();
|
||||
|
||||
ns_mgr.Ns_main().Case_match_(Xow_ns_case_.Tid__all);
|
||||
tstr.Run_parse("en.wiktionary.org/wiki/a").Chk_wiki("en.wiktionary.org").Chk_page("a");
|
||||
tstr.Exec__parse("en.wiktionary.org/wiki/a").Test__wiki("en.wiktionary.org").Test__page("a");
|
||||
|
||||
ns_mgr.Ns_category().Case_match_(Xow_ns_case_.Tid__all);
|
||||
tstr.Run_parse("en.wiktionary.org/wiki/Category:a").Chk_wiki("en.wiktionary.org").Chk_page("Category:a");
|
||||
tstr.Exec__parse("en.wiktionary.org/wiki/Category:a").Test__wiki("en.wiktionary.org").Test__page("Category:a");
|
||||
|
||||
tstr.Run_parse("en.wiktionary.org/wiki/A/B/C").Chk_page("A/B/C");
|
||||
tstr.Exec__parse("en.wiktionary.org/wiki/A/B/C").Test__page("A/B/C");
|
||||
}
|
||||
@Test public void Xwiki__to_enwiki() { // PURPOSE: handle alias of "wikipedia" and sv.wikipedia.org/wiki/Wikipedia:Main_Page; DATE:2015-07-31
|
||||
Xowe_wiki xwiki = tstr.Prep_create_wiki("sv.wikipedia.org");
|
||||
tstr.Prep_xwiki(xwiki, "wikipedia", "en.wikipedia.org", null);
|
||||
tstr.Prep_get_ns_mgr_from_meta("sv.wikipedia.org").Add_new(Xow_ns_.Tid__project, "Wikipedia");
|
||||
tstr.Run_parse(xwiki, "sv.wikipedia.org/wiki/wikipedia:X").Chk_wiki("sv.wikipedia.org").Chk_page("wikipedia:X");
|
||||
tstr.Run_parse(xwiki, "sv.wikipedia.org/wiki/Wikipedia:X").Chk_wiki("sv.wikipedia.org").Chk_page("Wikipedia:X");
|
||||
tstr.Exec__parse(xwiki, "sv.wikipedia.org/wiki/wikipedia:X").Test__wiki("sv.wikipedia.org").Test__page("wikipedia:X");
|
||||
tstr.Exec__parse(xwiki, "sv.wikipedia.org/wiki/Wikipedia:X").Test__wiki("sv.wikipedia.org").Test__page("Wikipedia:X");
|
||||
}
|
||||
@Test public void Xwiki__to_ns() { // PURPOSE: handle alias of "wikipedia" in current, but no "Wikipedia" ns in other wiki; PAGE:pt.w:Wikipedia:P<>gina_de_testes DATE:2015-09-17
|
||||
tstr.Prep_create_wiki("pt.wikipedia.org");
|
||||
tstr.Prep_get_ns_mgr_from_meta("pt.wikipedia.org").Add_new(Xow_ns_.Tid__project, "Project"); // clear ns_mgr and add only "Project" ns, not "Wikipedia" ns
|
||||
tstr.Prep_xwiki(tstr.Wiki(), "wikipedia", "en.wikipedia.org", null); // add alias of "wikipedia" in current wiki
|
||||
tstr.Run_parse(tstr.Wiki(), "pt.wikipedia.org/wiki/Wikipedia:X").Chk_wiki("pt.wikipedia.org").Chk_page("Wikipedia:X"); // should get "pt.wikipedia.org", not "en.wikipedia.org" (through alias)
|
||||
tstr.Exec__parse(tstr.Wiki(), "pt.wikipedia.org/wiki/Wikipedia:X").Test__wiki("pt.wikipedia.org").Test__page("Wikipedia:X"); // should get "pt.wikipedia.org", not "en.wikipedia.org" (through alias)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -46,36 +46,36 @@ public class Xow_url_parser_fxt {
|
||||
public Xow_ns_mgr Prep_get_ns_mgr_from_meta(String wiki) {
|
||||
return app.Dbmeta_mgr().Ns__get_or_load(Bry_.new_u8(wiki));
|
||||
}
|
||||
public Xow_url_parser_fxt Run_parse(String actl_str) {return Run_parse(cur_wiki, actl_str);}
|
||||
public Xow_url_parser_fxt Run_parse(Xow_wiki wiki, String actl_str) {
|
||||
public Xow_url_parser_fxt Exec__parse(String actl_str) {return Exec__parse(cur_wiki, actl_str);}
|
||||
public Xow_url_parser_fxt Exec__parse(Xow_wiki wiki, String actl_str) {
|
||||
this.actl_url = wiki.Utl__url_parser().Parse(Bry_.new_u8(actl_str));
|
||||
return this;
|
||||
}
|
||||
public Xow_url_parser_fxt Run_parse_reuse(String actl_str) {
|
||||
public Xow_url_parser_fxt Exec__parse_reuse(String actl_str) {
|
||||
this.actl_url = parser.Parse(Bry_.new_u8(actl_str));
|
||||
return this;
|
||||
}
|
||||
public Xow_url_parser_fxt Run_parse_from_url_bar(String raw) {
|
||||
public Xow_url_parser_fxt Exec__parse_from_url_bar(String raw) {
|
||||
this.actl_url = parser.Parse_by_urlbar_or_null(raw);
|
||||
return this;
|
||||
}
|
||||
public Xow_url_parser_fxt Chk_tid(int v) {Tfds.Eq_int(v, actl_url.Tid() , "tid"); return this;}
|
||||
public Xow_url_parser_fxt Chk_is_null() {Tfds.Eq_bool(true, actl_url == null); return this;}
|
||||
public Xow_url_parser_fxt Chk_vnt(String v) {Tfds.Eq_str(v, actl_url.Vnt_bry() , "vnt"); return this;}
|
||||
public Xow_url_parser_fxt Chk_wiki(String v) {Tfds.Eq_str(v, actl_url.Wiki_bry() , "wiki"); return this;}
|
||||
public Xow_url_parser_fxt Chk_wiki_is_missing(boolean v) {Tfds.Eq_bool(v, actl_url.Wiki_is_missing(), "wiki_is_missing"); return this;}
|
||||
public Xow_url_parser_fxt Chk_page(String v) {Tfds.Eq_str(v, actl_url.Page_bry() , "page"); return this;}
|
||||
public Xow_url_parser_fxt Chk_qargs(String v) {Tfds.Eq_str(v, actl_url.Qargs_mgr().To_bry(), "qargs"); return this;}
|
||||
public Xow_url_parser_fxt Chk_page_is_main_y() {return Chk_page_is_main(Bool_.Y);}
|
||||
public Xow_url_parser_fxt Chk_page_is_main_n() {return Chk_page_is_main(Bool_.N);}
|
||||
public Xow_url_parser_fxt Chk_page_is_main(boolean v) {Tfds.Eq_bool(v, actl_url.Page_is_main() , "page_is_main"); return this;}
|
||||
public Xow_url_parser_fxt Chk_anch(String v) {Tfds.Eq_str(v, actl_url.Anch_bry(), "anch"); return this;}
|
||||
public Xow_url_parser_fxt Chk_action_is_edit_y() {return Chk_action_is_edit_(Bool_.Y);}
|
||||
public Xow_url_parser_fxt Chk_action_is_edit_n() {return Chk_action_is_edit_(Bool_.N);}
|
||||
private Xow_url_parser_fxt Chk_action_is_edit_(boolean v) {Tfds.Eq_bool(v, actl_url.Qargs_mgr().Match(Xoa_url_.Qarg__action, Xoa_url_.Qarg__action__edit), "action_is_edit"); return this;}
|
||||
public Xow_url_parser_fxt Chk_to_str(String v) {return Chk_to_str(Bool_.Y, v);}
|
||||
public Xow_url_parser_fxt Chk_to_str(boolean full, String v) {Tfds.Eq_str(v, actl_url.To_bry(full, Bool_.Y), "To_bry"); return this;}
|
||||
public Xow_url_parser_fxt Chk_build_str_is_same() {
|
||||
public Xow_url_parser_fxt Test__tid(int v) {Tfds.Eq_int(v, actl_url.Tid() , "tid"); return this;}
|
||||
public Xow_url_parser_fxt Test__is_null() {Tfds.Eq_bool(true, actl_url == null); return this;}
|
||||
public Xow_url_parser_fxt Test__vnt(String v) {Tfds.Eq_str(v, actl_url.Vnt_bry() , "vnt"); return this;}
|
||||
public Xow_url_parser_fxt Test__wiki(String v) {Tfds.Eq_str(v, actl_url.Wiki_bry() , "wiki"); return this;}
|
||||
public Xow_url_parser_fxt Test__wiki_is_missing(boolean v) {Tfds.Eq_bool(v, actl_url.Wiki_is_missing(), "wiki_is_missing"); return this;}
|
||||
public Xow_url_parser_fxt Test__page(String v) {Tfds.Eq_str(v, actl_url.Page_bry() , "page"); return this;}
|
||||
public Xow_url_parser_fxt Test__qargs(String v) {Tfds.Eq_str(v, actl_url.Qargs_mgr().To_bry(), "qargs"); return this;}
|
||||
public Xow_url_parser_fxt Test__page_is_main_y() {return Test__page_is_main(Bool_.Y);}
|
||||
public Xow_url_parser_fxt Test__page_is_main_n() {return Test__page_is_main(Bool_.N);}
|
||||
public Xow_url_parser_fxt Test__page_is_main(boolean v) {Tfds.Eq_bool(v, actl_url.Page_is_main() , "page_is_main"); return this;}
|
||||
public Xow_url_parser_fxt Test__anch(String v) {Tfds.Eq_str(v, actl_url.Anch_bry(), "anch"); return this;}
|
||||
public Xow_url_parser_fxt Test__action_is_edit_y() {return Test__action_is_edit_(Bool_.Y);}
|
||||
public Xow_url_parser_fxt Test__action_is_edit_n() {return Test__action_is_edit_(Bool_.N);}
|
||||
private Xow_url_parser_fxt Test__action_is_edit_(boolean v) {Tfds.Eq_bool(v, actl_url.Qargs_mgr().Match(Xoa_url_.Qarg__action, Xoa_url_.Qarg__action__edit), "action_is_edit"); return this;}
|
||||
public Xow_url_parser_fxt Test__to_str(String v) {return Test__to_str(Bool_.Y, v);}
|
||||
public Xow_url_parser_fxt Test__to_str(boolean full, String v) {Tfds.Eq_str(v, actl_url.To_bry(full, Bool_.Y), "To_bry"); return this;}
|
||||
public Xow_url_parser_fxt Test__build_str_is_same() {
|
||||
Xow_url_parser parser = new Xow_url_parser(cur_wiki);
|
||||
Tfds.Eq_str(actl_url.Raw(), parser.Build_str(actl_url), "build_str");
|
||||
return this;
|
||||
|
||||
@@ -46,7 +46,8 @@ public class Xoapi_orig_wmf extends Xoapi_orig_base {
|
||||
|
||||
if (Parse_xml_val(tmp_rng, usr_dlg, xml, xml_len, pos, Bry_xml_descriptionurl)) {
|
||||
byte[] file_url = Bry_.Mid(xml, tmp_rng.Val_0(), tmp_rng.Val_1());
|
||||
orig_wiki = gplx.xowa.wikis.xwikis.Xow_xwiki_mgr.Get_domain_from_url(url_parser, url, file_url);
|
||||
Gfo_url url = url_parser.Parse(file_url, 0, file_url.length);
|
||||
orig_wiki = url.Segs__get_at_1st();
|
||||
byte[] page = Xoa_ttl.Replace_spaces(url.Segs__get_at_nth());
|
||||
int colon_pos = Bry_find_.Find_fwd(page, Byte_ascii.Colon, 0, page.length);
|
||||
if (colon_pos != Bry_find_.Not_found)
|
||||
@@ -58,7 +59,7 @@ public class Xoapi_orig_wmf extends Xoapi_orig_base {
|
||||
}
|
||||
}
|
||||
private static Int_2_ref tmp_rng = new Int_2_ref();
|
||||
private static Gfo_url_parser url_parser = new Gfo_url_parser(); private static Gfo_url url = new Gfo_url();
|
||||
private static Gfo_url_parser url_parser = new Gfo_url_parser();
|
||||
private static boolean Parse_xml_val(Int_2_ref rv, Gfo_usr_dlg usr_dlg, byte[] xml, int xml_len, int pos, byte[] key) {
|
||||
int bgn = 0, end = 0;
|
||||
bgn = Bry_find_.Find_fwd(xml, key, pos, xml_len); if (bgn == Bry_find_.Not_found) return false;
|
||||
|
||||
@@ -17,9 +17,10 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.bldrs; import gplx.*; import gplx.xowa.*;
|
||||
import gplx.core.consoles.*; import gplx.core.envs.*;
|
||||
import gplx.xowa.apps.*; import gplx.xowa.bldrs.*; import gplx.xowa.bldrs.xmls.*; import gplx.xowa.bldrs.cfgs.*; import gplx.xowa.langs.bldrs.*;
|
||||
import gplx.xowa.apps.*; import gplx.xowa.bldrs.*; import gplx.xowa.bldrs.xmls.*; import gplx.xowa.langs.bldrs.*;
|
||||
import gplx.xowa.bldrs.wkrs.*;
|
||||
import gplx.langs.jsons.*;
|
||||
import gplx.xowa.addons.bldrs.app_cfgs.*;
|
||||
public class Xob_bldr implements Gfo_invk {
|
||||
private boolean pause_at_end = false; private long prv_prog_time; private Xob_xml_parser dump_parser;
|
||||
public Xob_bldr(Xoae_app app) {
|
||||
|
||||
@@ -36,7 +36,7 @@ public class Xob_page_wkr_cmd implements Xob_cmd {
|
||||
gplx.core.ios.streams.Io_stream_rdr src_rdr = wiki.Import_cfg().Src_rdr();
|
||||
fil = Io_buffer_rdr.new_(src_rdr, optRdrBfrSize);
|
||||
fil_len = fil.Fil_len();
|
||||
if (src_rdr.Tid() == gplx.core.ios.streams.Io_stream_.Tid_bzip2) fil_len = (fil_len * 100) / 18; // HACK: no way to get actual file progress; assume 18% compression
|
||||
if (src_rdr.Tid() == gplx.core.ios.streams.Io_stream_tid_.Tid__bzip2) fil_len = (fil_len * 100) / 18; // HACK: no way to get actual file progress; assume 18% compression
|
||||
// fil.Seek(bldr.Opts().ResumeAt());
|
||||
int prv_pos = 0;
|
||||
while (true) {
|
||||
|
||||
@@ -107,7 +107,7 @@ public class Xob_make_cmd_site implements Io_make_cmd {
|
||||
fil_wtr.Add_idx_direct(itm_len, Byte_.Zero);
|
||||
Io_stream_wtr wtr = null;
|
||||
try {
|
||||
wtr = Io_stream_wtr_.file_(fil_wtr.Fil_url());
|
||||
wtr = Io_stream_wtr_.New__raw(fil_wtr.Fil_url());
|
||||
wtr.Open();
|
||||
fil_wtr.FlushIdx(wtr);
|
||||
wtr.Write(bry, itm_bgn, itm_end);
|
||||
|
||||
@@ -30,9 +30,9 @@ public class Xob_unzip_wkr {
|
||||
}
|
||||
public void Decompress(Io_url src, Io_url trg) {
|
||||
String src_ext = src.Ext();
|
||||
if (String_.Eq(src_ext, gplx.core.ios.streams.Io_stream_.Ext_bz2)) process = decompress_bz2;
|
||||
else if (String_.Eq(src_ext, gplx.core.ios.streams.Io_stream_.Ext_zip)) process = decompress_zip;
|
||||
else if (String_.Eq(src_ext, gplx.core.ios.streams.Io_stream_.Ext_gz)) process = decompress_gz;
|
||||
if (String_.Eq(src_ext, gplx.core.ios.streams.Io_stream_tid_.Ext__bz2)) process = decompress_bz2;
|
||||
else if (String_.Eq(src_ext, gplx.core.ios.streams.Io_stream_tid_.Ext__zip)) process = decompress_zip;
|
||||
else if (String_.Eq(src_ext, gplx.core.ios.streams.Io_stream_tid_.Ext__gz)) process = decompress_gz;
|
||||
else throw Err_.new_unhandled(src_ext);
|
||||
Io_url trg_owner_dir = trg.OwnerDir();
|
||||
Io_mgr.Instance.CreateDirIfAbsent(trg_owner_dir);
|
||||
|
||||
@@ -240,7 +240,6 @@ public class Xoa_css_extractor {
|
||||
int prv_pos = 0;
|
||||
int css_find_bgn_len = Css_find_bgn.length;
|
||||
byte[] protocol_prefix_bry = Bry_.new_u8(protocol_prefix);
|
||||
Gfo_url gfo_url = new Gfo_url();
|
||||
while (true) {
|
||||
int url_bgn = Bry_find_.Find_fwd(raw, Css_find_bgn, prv_pos); if (url_bgn == Bry_find_.Not_found) break; // nothing left; stop
|
||||
url_bgn += css_find_bgn_len;
|
||||
@@ -249,7 +248,7 @@ public class Xoa_css_extractor {
|
||||
css_url_bry = Bry_.Replace(css_url_bry, Css_amp_find, Css_amp_repl); // & -> &
|
||||
css_url_bry = url_encoder.Decode(css_url_bry); // %2C -> %7C -> |
|
||||
css_url_bry = Xoa_css_extractor.Url_root_fix(wiki_domain, css_url_bry);
|
||||
url_parser.Parse(gfo_url, css_url_bry, 0, css_url_bry.length);
|
||||
Gfo_url gfo_url = url_parser.Parse(css_url_bry, 0, css_url_bry.length);
|
||||
if ( gfo_url.Protocol_tid() == Gfo_protocol_itm.Tid_relative_1 // if rel url, add protocol_prefix DATE:2015-08-01
|
||||
|| (Env_.Mode_testing() && gfo_url.Protocol_tid() == Gfo_protocol_itm.Tid_unknown)) // TEST:
|
||||
css_url_bry = Bry_.Add(protocol_prefix_bry, css_url_bry);
|
||||
|
||||
@@ -21,7 +21,7 @@ import gplx.xowa.bldrs.wms.dumps.*;
|
||||
public class Xoi_dump_mgr implements Gfo_invk {
|
||||
public String[] Server_urls() {return server_urls;} private String[] server_urls = String_.Ary(Xowm_dump_file_.Server_your_org, Xowm_dump_file_.Server_wmf_https, Xowm_dump_file_.Server_c3sl, Xowm_dump_file_.Server_masaryk); // promote your.org to primary url; DATE:2016-08-07
|
||||
public String[] Custom_cmds() {return custom_cmds;} private String[] custom_cmds = String_.Ary(Xoi_cmd_wiki_download.Key_wiki_download, Xoi_cmd_wiki_import.KEY);
|
||||
public byte Data_storage_format() {return data_storage_format;} public Xoi_dump_mgr Data_storage_format_(byte v) {data_storage_format = v; return this;} private byte data_storage_format = gplx.core.ios.streams.Io_stream_.Tid_gzip;
|
||||
public byte Data_storage_format() {return data_storage_format;} public Xoi_dump_mgr Data_storage_format_(byte v) {data_storage_format = v; return this;} private byte data_storage_format = gplx.core.ios.streams.Io_stream_tid_.Tid__gzip;
|
||||
public long Db_text_max() {return db_text_max;} private long db_text_max = (long)3000 * Io_mgr.Len_mb;
|
||||
public long Db_categorylinks_max() {return db_categorylinks_max;} private long db_categorylinks_max = (long)3600 * Io_mgr.Len_mb;
|
||||
public long Db_wikidata_max() {return db_wikidata_max;} private long db_wikidata_max = (long)3600 * Io_mgr.Len_mb;
|
||||
@@ -38,8 +38,8 @@ public class Xoi_dump_mgr implements Gfo_invk {
|
||||
else if (ctx.Match(k, Invk_server_urls_)) server_urls = m.ReadStrAryIgnore("v", ",", "\n");
|
||||
else if (ctx.Match(k, Invk_custom_cmds)) return String_.Concat_with_str(",", custom_cmds);
|
||||
else if (ctx.Match(k, Invk_custom_cmds_)) custom_cmds = String_.Ary_filter(m.ReadStrAry("v", ","), Xoi_cmd_mgr.Wiki_cmds_valid);
|
||||
else if (ctx.Match(k, Invk_data_storage_format)) return Io_stream_.Obsolete_to_str(data_storage_format);
|
||||
else if (ctx.Match(k, Invk_data_storage_format_)) data_storage_format = Io_stream_.Obsolete_to_tid(m.ReadStr("v"));
|
||||
else if (ctx.Match(k, Invk_data_storage_format)) return Io_stream_tid_.Obsolete_to_str(data_storage_format);
|
||||
else if (ctx.Match(k, Invk_data_storage_format_)) data_storage_format = Io_stream_tid_.Obsolete_to_tid(m.ReadStr("v"));
|
||||
else if (ctx.Match(k, Invk_data_storage_format_list)) return Options_data_storage_format_list;
|
||||
else if (ctx.Match(k, Invk_db_text_max)) return db_text_max / Io_mgr.Len_mb;
|
||||
else if (ctx.Match(k, Invk_db_text_max_)) db_text_max = m.ReadLong("v") * Io_mgr.Len_mb;
|
||||
|
||||
@@ -32,7 +32,7 @@ public class Xosql_dump_parser {
|
||||
try {
|
||||
// init bfrs, rdr
|
||||
Bry_bfr val_bfr = Bry_bfr_.New();
|
||||
rdr = Io_buffer_rdr.new_(Io_stream_rdr_.new_by_url_(src_fil), src_rdr_bfr_len);
|
||||
rdr = Io_buffer_rdr.new_(Io_stream_rdr_.New_by_url(src_fil), src_rdr_bfr_len);
|
||||
byte[] bfr = rdr.Bfr(); int bfr_len = rdr.Bfr_len(), fld_idx = 0, cur_pos = 0;
|
||||
|
||||
this.tbl_flds = Identify_flds(cbk_flds, bfr);
|
||||
|
||||
@@ -18,7 +18,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
package gplx.xowa.bldrs.wiki_cfgs; import gplx.*; import gplx.xowa.*; import gplx.xowa.bldrs.*;
|
||||
import org.junit.*; import gplx.core.strings.*;
|
||||
import gplx.langs.xmls.*;
|
||||
import gplx.xowa.bldrs.cfgs.*;
|
||||
import gplx.xowa.addons.bldrs.app_cfgs.*;
|
||||
public class Xoi_wiki_props_api_tst {
|
||||
private Xoi_wiki_props_fxt fxt = new Xoi_wiki_props_fxt();
|
||||
@Before public void init() {} // private Xob_subpage_tst_fxt fxt = new] Xob_subpage_tst_fxt();
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user