mirror of
https://github.com/gnosygnu/xowa.git
synced 2026-03-02 03:49:30 +00:00
v3.2.1.1
This commit is contained in:
@@ -16,10 +16,10 @@ 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.dbs; import gplx.*;
|
||||
import gplx.dbs.metas.*; import gplx.dbs.sqls.*;
|
||||
import gplx.dbs.metas.*; import gplx.dbs.sqls.*; import gplx.dbs.sqls.wtrs.*;
|
||||
class Db_diff_bldr {
|
||||
private final Bry_bfr bfr = Bry_bfr.new_();
|
||||
private final Db_sqlbldr__sqlite sql_bldr = new Db_sqlbldr__sqlite();
|
||||
private final Sql_schema_wtr sql_bldr = new Sql_schema_wtr();
|
||||
public Db_diff_bldr() {sql_bldr.Bfr_(bfr);}
|
||||
public String Compare_db(String src_str, String trg_str) {
|
||||
// Io_url src_url = Io_url_.new_fil_(src_str);
|
||||
|
||||
@@ -76,7 +76,7 @@ public class Fsd_fil_tbl implements Rls_able {
|
||||
}
|
||||
public Fsd_fil_itm Select_or_null(int dir_id, byte[] fil_name) {
|
||||
if (stmt_select_by_name == null) {
|
||||
Db_qry__select_cmd qry = Db_qry__select_cmd.new_().From_(tbl_name).Cols_(flds.To_str_ary()).Where_(Db_crt_.eq_many_(fld_owner_id, fld_name)).Indexed_by_(idx_owner);
|
||||
Db_qry__select_cmd qry = new Db_qry__select_cmd().From_(tbl_name).Cols_(flds.To_str_ary()).Where_(Db_crt_.eq_many_(fld_owner_id, fld_name)).Indexed_by_(idx_owner);
|
||||
stmt_select_by_name = conn.Stmt_new(qry);
|
||||
}
|
||||
Db_rdr rdr = stmt_select_by_name.Clear()
|
||||
|
||||
@@ -34,7 +34,7 @@ public class Xoa_app_ {
|
||||
}
|
||||
}
|
||||
public static final String Name = "xowa";
|
||||
public static final String Version = "3.1.5.1";
|
||||
public static final String Version = "3.2.1.1";
|
||||
public static String Build_date = "2012-12-30 00:00:00";
|
||||
public static String Op_sys_str;
|
||||
public static String User_agent = "";
|
||||
|
||||
@@ -45,6 +45,18 @@ public class Xoa_test_ {
|
||||
Db_conn_bldr.Instance.Reg_default_sqlite();
|
||||
}
|
||||
}
|
||||
public static String Db__print_tbl_as_str(Bry_bfr bfr, Db_conn conn, String tbl, String... cols) {
|
||||
int cols_len = cols.length;
|
||||
Db_rdr rdr = conn.Stmt_select(tbl, cols).Exec_select__rls_auto();
|
||||
while (rdr.Move_next()) {
|
||||
for (int i = 0; i < cols_len; ++i) {
|
||||
bfr.Add_obj(rdr.Read_at(i));
|
||||
bfr.Add_byte(i == cols_len - 1 ? Byte_ascii.Nl : Byte_ascii.Pipe);
|
||||
}
|
||||
}
|
||||
rdr.Rls();
|
||||
return bfr.To_str_and_clear();
|
||||
}
|
||||
public static void Inet__init() {
|
||||
Gfo_inet_conn_.new_prototype_(Gfo_inet_conn_.Tid__mem__hash);
|
||||
}
|
||||
|
||||
@@ -49,7 +49,7 @@ class Xob_dump_src_id {
|
||||
cur_text_db_idx = text_db_idx;
|
||||
Xowd_db_file text_db = db_mgr.Core_data_mgr().Dbs__get_at(text_db_idx);
|
||||
Db_conn conn = text_db.Conn();
|
||||
String sql = String_.Format(Sql_select, New_rdr__redirect_clause(redirect));
|
||||
String sql = String_.Format(Sql_select_itm, New_rdr__redirect_clause(redirect));
|
||||
text_stmt = conn.Stmt_new(Db_qry_sql.rdr_(sql));
|
||||
}
|
||||
return text_stmt.Clear().Val_int(prv_id).Val_int(cur_ns).Exec_select();
|
||||
@@ -75,7 +75,7 @@ class Xob_dump_src_id {
|
||||
default: throw Err_.new_unhandled(redirect);
|
||||
}
|
||||
}
|
||||
private static final String Sql_select = String_.Concat_lines_nl
|
||||
private static final String Sql_select_itm = String_.Concat_lines_nl
|
||||
( "SELECT p.page_id"
|
||||
, ", p.page_title"
|
||||
, ", t.text_data"
|
||||
|
||||
@@ -96,7 +96,7 @@ class Db_tst_qry {
|
||||
DataRdr rdr = DataRdr_.Null;
|
||||
Bry_bfr bfr = Bry_bfr.new_();
|
||||
try {
|
||||
rdr = conn.Exec_qry_as_rdr(qry);
|
||||
rdr = conn.Exec_qry_as_old_rdr(qry);
|
||||
int expd_row_idx = 0, expd_row_max = rows.Count();
|
||||
while (rdr.MoveNextPeer()) {
|
||||
if (expd_row_idx == expd_row_max) break;
|
||||
@@ -127,11 +127,11 @@ class Db_tst_qry {
|
||||
}
|
||||
if (!pass) {
|
||||
bfr.Add(Lbl_row_hdr).Add_int_variable(expd_row_idx).Add_byte_nl();
|
||||
bfr.Add_str_u8(qry.Xto_sql()).Add_byte(Byte_ascii.Semic);
|
||||
bfr.Add_str_u8(qry.To_sql__exec(gplx.dbs.sqls.Sql_qry_wtr_.Sqlite)).Add_byte(Byte_ascii.Semic);
|
||||
throw Err_.new_wo_type(bfr.To_str_and_clear());
|
||||
}
|
||||
} static final byte[] Lbl_row_hdr = Bry_.new_a7("row: "), Lbl_eq_y = Bry_.new_a7(" == "), Lbl_eq_n = Bry_.new_a7(" != ");
|
||||
public static Db_tst_qry tbl_(String tbl_name, String order_by) {return new_(Db_qry_.select_tbl_(tbl_name).OrderBy_asc_(order_by));}
|
||||
public static Db_tst_qry tbl_(String tbl_name, String order_by) {return new_(Db_qry_.select_tbl_(tbl_name).Order_asc_(order_by));}
|
||||
public static Db_tst_qry new_(Db_qry qry) {
|
||||
Db_tst_qry rv = new Db_tst_qry();
|
||||
rv.qry = qry;
|
||||
|
||||
@@ -19,16 +19,19 @@ package gplx.xowa.bldrs.cmds.diffs; import gplx.*; import gplx.xowa.*; import gp
|
||||
public class Xob_diff_build_cmd implements Xob_cmd {
|
||||
private final Xob_bldr bldr; private final Xowe_wiki wiki;
|
||||
private String prev_url, curr_url, diff_url; private int commit_interval;
|
||||
private int[] db_ids = Int_.Ary_empty; private String bld_name = "all";
|
||||
public Xob_diff_build_cmd(Xob_bldr bldr, Xowe_wiki wiki) {this.bldr = bldr; this.wiki = wiki;}
|
||||
public String Cmd_key() {return Xob_cmd_keys.Key_diff_build;}
|
||||
public void Cmd_run() {
|
||||
new Xob_diff_build_wkr(bldr, wiki, prev_url, curr_url, diff_url, commit_interval).Exec();
|
||||
new Xob_diff_build_wkr(bldr, wiki, prev_url, curr_url, diff_url, commit_interval, new Xowd_tbl_mapr(bld_name, db_ids)).Exec();
|
||||
}
|
||||
public Object Invk(GfsCtx ctx, int ikey, String k, GfoMsg m) {
|
||||
if (ctx.Match(k, Invk__prev_url_)) prev_url = m.ReadStr("v");
|
||||
else if (ctx.Match(k, Invk__curr_url_)) curr_url = m.ReadStr("v");
|
||||
else if (ctx.Match(k, Invk__diff_url_)) diff_url = m.ReadStr("v");
|
||||
else if (ctx.Match(k, Invk__commit_interval_)) commit_interval = m.ReadInt("v");
|
||||
else if (ctx.Match(k, Invk__db_ids_)) db_ids = Int_.Ary_parse(m.ReadStr("v"), "|");
|
||||
else if (ctx.Match(k, Invk__bld_name_)) bld_name = m.ReadStr("v");
|
||||
else return GfoInvkAble_.Rv_unhandled;
|
||||
return this;
|
||||
}
|
||||
@@ -36,5 +39,6 @@ public class Xob_diff_build_cmd implements Xob_cmd {
|
||||
public void Cmd_bgn(Xob_bldr bldr) {}
|
||||
public void Cmd_end() {}
|
||||
public void Cmd_term() {}
|
||||
private static final String Invk__prev_url_ = "prev_url_", Invk__curr_url_ = "curr_url_", Invk__diff_url_ = "diff_url_", Invk__commit_interval_ = "commit_interval_";
|
||||
private static final String Invk__prev_url_ = "prev_url_", Invk__curr_url_ = "curr_url_", Invk__diff_url_ = "diff_url_"
|
||||
, Invk__commit_interval_ = "commit_interval_", Invk__db_ids_ = "db_ids_", Invk__bld_name_ = "bld_name_";
|
||||
}
|
||||
|
||||
@@ -17,33 +17,42 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.bldrs.cmds.diffs; import gplx.*; import gplx.xowa.*; import gplx.xowa.bldrs.*; import gplx.xowa.bldrs.cmds.*;
|
||||
import gplx.core.brys.*; import gplx.core.brys.fmtrs.*;
|
||||
import gplx.dbs.*; import gplx.dbs.metas.*; import gplx.dbs.diffs.*; import gplx.dbs.diffs.builds.*;
|
||||
import gplx.dbs.*; import gplx.dbs.metas.*; import gplx.dbs.diffs.*; import gplx.dbs.diffs.builds.*; import gplx.dbs.diffs.itms.*;
|
||||
import gplx.xowa.wikis.data.*; import gplx.xowa.wikis.data.tbls.*;
|
||||
class Xob_diff_build_wkr {
|
||||
private final Gfdb_diff_bldr dif_bldr = new Gfdb_diff_bldr();
|
||||
private final Xowe_wiki wiki;
|
||||
private Db_conn old_conn, new_conn, dif_conn;
|
||||
public Xob_diff_build_wkr(Xob_bldr bldr, Xowe_wiki wiki, String old_url, String new_url, String dif_url, int commit_interval) {
|
||||
private final Xowd_tbl_mapr tbl_mapr;
|
||||
public Xob_diff_build_wkr(Xob_bldr bldr, Xowe_wiki wiki, String old_url, String new_url, String dif_url, int commit_interval, Xowd_tbl_mapr tbl_mapr) {
|
||||
this.wiki = wiki;
|
||||
wiki.Init_by_wiki();
|
||||
Bry_fmt url_fmt = Bry_fmt.New("").Args_(New_url_args(wiki));
|
||||
Bry_fmt url_fmt = Bry_fmt.New("").Args_(New_url_args(wiki, tbl_mapr.Name));
|
||||
Bry_bfr tmp_bfr = Bry_bfr.new_();
|
||||
old_conn = New_conn(Bool_.N, wiki, url_fmt, old_url, tmp_bfr);
|
||||
new_conn = New_conn(Bool_.N, wiki, url_fmt, new_url, tmp_bfr);
|
||||
dif_conn = New_conn(Bool_.Y, wiki, url_fmt, dif_url, tmp_bfr);
|
||||
old_conn = New_conn(tmp_bfr, wiki, url_fmt, Bool_.N, old_url);
|
||||
new_conn = New_conn(tmp_bfr, wiki, url_fmt, Bool_.N, new_url);
|
||||
dif_conn = New_conn(tmp_bfr, wiki, url_fmt, Bool_.Y, dif_url);
|
||||
this.tbl_mapr = tbl_mapr;
|
||||
}
|
||||
public void Exec() {
|
||||
Gfdb_diff_db dif_db = new Gfdb_diff_db(dif_conn);
|
||||
Gdif_core dif_core = new Gdif_core(dif_conn);
|
||||
String name = String_.Format("{0}|{1}|diffs|{2}", wiki.Domain_str(), tbl_mapr.Name, wiki.Props().Modified_latest().XtoStr_fmt(DateAdp_.Fmt__yyyyMMdd)); // EX: "simple.wikipedia.org|text|diffs|20160112"
|
||||
String made_by = wiki.App().User().Key();
|
||||
Gdif_job_itm job_itm = dif_core.New_job(name, made_by);
|
||||
Gdif_bldr_ctx ctx = new Gdif_bldr_ctx().Init(dif_core, job_itm);
|
||||
|
||||
Gfdb_diff_wkr__db dif_wkr = new Gfdb_diff_wkr__db();
|
||||
Gdif_db dif_db = dif_core.Db();
|
||||
dif_wkr.Init_conn(dif_db, 1000);
|
||||
dif_bldr.Init(dif_wkr);
|
||||
Dbmeta_tbl_mgr old_tbl_mgr = old_conn.Meta_tbl_load_all();
|
||||
Dbmeta_tbl_mgr new_tbl_mgr = old_conn.Meta_tbl_load_all();
|
||||
int new_tbl_len = new_tbl_mgr.Len();
|
||||
int txn = -1;
|
||||
for (int i = 0; i < new_tbl_len; ++i) {
|
||||
Dbmeta_tbl_itm new_tbl = new_tbl_mgr.Get_at(i);
|
||||
Dbmeta_tbl_itm old_tbl = old_tbl_mgr.Get_by(new_tbl.Name()); if (old_tbl == null) continue;
|
||||
Gfdb_diff_tbl dif_tbl = Gfdb_diff_tbl.New(new_tbl);
|
||||
dif_bldr.Compare(++txn, dif_tbl, old_conn, new_conn);
|
||||
// save txn
|
||||
|
||||
// wiki.Data__core_mgr().Db__core().Conn().Conn_info();
|
||||
Xowd_db_file[] db_files = wiki.Data__core_mgr().Db__core().Tbl__db().Select_all(wiki.Data__core_mgr().Props(), Io_url_.Empty);
|
||||
int db_files_len = db_files.length;
|
||||
for (int i = 0; i < db_files_len; ++i) {
|
||||
Xowd_db_file db_file = db_files[i];
|
||||
if (tbl_mapr.Db_ids__has(db_file.Tid()))
|
||||
Compare(ctx);
|
||||
}
|
||||
// int old_tbl_len = old_tbl_mgr.Len();
|
||||
// for (int i = 0; i < old_tbl_len; ++i) {
|
||||
@@ -54,20 +63,35 @@ class Xob_diff_build_wkr {
|
||||
// }
|
||||
// }
|
||||
}
|
||||
public static Db_conn New_conn(boolean autocreate, Xow_wiki wiki, Bry_fmt fmtr, String url_fmt, Bry_bfr tmp_bfr) {
|
||||
fmtr.Fmt_(url_fmt).Bld_bfr_many(tmp_bfr);
|
||||
private void Compare(Gdif_bldr_ctx ctx) {
|
||||
Dbmeta_tbl_mgr old_tbl_mgr = old_conn.Meta_tbl_load_all();
|
||||
Dbmeta_tbl_mgr new_tbl_mgr = old_conn.Meta_tbl_load_all();
|
||||
int new_tbl_len = new_tbl_mgr.Len();
|
||||
for (int i = 0; i < new_tbl_len; ++i) {
|
||||
Dbmeta_tbl_itm new_tbl = new_tbl_mgr.Get_at(i);
|
||||
Dbmeta_tbl_itm old_tbl = old_tbl_mgr.Get_by(new_tbl.Name()); if (old_tbl == null) continue;
|
||||
Gfdb_diff_tbl dif_tbl = Gfdb_diff_tbl.New(new_tbl);
|
||||
dif_bldr.Compare(ctx, dif_tbl, old_conn, new_conn);
|
||||
// save txn
|
||||
}
|
||||
}
|
||||
public static Db_conn New_conn(Bry_bfr tmp_bfr, Xow_wiki wiki, Bry_fmt fmtr, boolean autocreate, String url_fmt) {
|
||||
fmtr.Fmt_(url_fmt).Bld_many(tmp_bfr);
|
||||
return Db_conn_bldr.Instance.Get_or_autocreate(autocreate, Io_url_.new_any_(tmp_bfr.To_str_and_clear()));
|
||||
}
|
||||
private static Bfr_fmt_arg[] New_url_args(Xow_wiki wiki) {
|
||||
private static Bfr_fmt_arg[] New_url_args(Xow_wiki wiki, String db_mapr_name) {
|
||||
Bfr_fmt_arg[] rv = new Bfr_fmt_arg[]
|
||||
{ new Bfr_fmt_arg(Bry_.new_a7(".dump_dir"), new Bfr_arg__dump_dir(wiki))
|
||||
, new Bfr_fmt_arg(Bry_.new_a7(".dump_core"), new Bfr_arg__dump_core(wiki))
|
||||
, new Bfr_fmt_arg(Bry_.new_a7(".dump_domain"), new Bfr_arg__dump_domain(wiki))
|
||||
, new Bfr_fmt_arg(Bry_.new_a7(".dir_spr"), new Bfr_arg__dir_spr())
|
||||
, new Bfr_fmt_arg(Bry_.new_a7(".dif_name"), Bfr_arg_.New_bry(db_mapr_name))
|
||||
};
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
//old_url='~{.dump_dir}-prev/~{.dump_core}';
|
||||
//new_url='~{.dump_dir}/~{.dump_core}';
|
||||
//dif_url='~{.dump_dir}/~{.dump_domain}-diff.xowa';
|
||||
//dif_url='~{.dump_dir}/~{.dump_domain}-{.dif_name}-diff.xowa';
|
||||
// old_conn='data source="~{.dump_dir}/~{.dump_core}";url='
|
||||
// dif_conn='gplx_key=sqlite;url='
|
||||
}
|
||||
|
||||
@@ -15,17 +15,20 @@ 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.cmds.randoms; import gplx.*; import gplx.xowa.*; import gplx.xowa.bldrs.*; import gplx.xowa.bldrs.cmds.*;
|
||||
public class Xob_rnd_cmd implements Xob_cmd {
|
||||
// private final Xob_bldr bldr; private final Xowe_wiki wiki;
|
||||
public Xob_rnd_cmd(Xob_bldr bldr, Xowe_wiki wiki) {}//this.bldr = bldr; this.wiki = wiki;}
|
||||
public String Cmd_key() {return Xob_cmd_keys.Key_util_random;}
|
||||
public void Cmd_run() {
|
||||
package gplx.xowa.bldrs.cmds.diffs; import gplx.*; import gplx.xowa.*; import gplx.xowa.bldrs.*; import gplx.xowa.bldrs.cmds.*;
|
||||
import gplx.xowa.wikis.data.*;
|
||||
class Xowd_tbl_mapr {
|
||||
public Xowd_tbl_mapr(String name, int[] db_ids) {
|
||||
this.Name = name;
|
||||
this.Db_ids = db_ids;
|
||||
}
|
||||
public Object Invk(GfsCtx ctx, int ikey, String k, GfoMsg m) {return this;}
|
||||
|
||||
public void Cmd_init(Xob_bldr bldr) {}
|
||||
public void Cmd_bgn(Xob_bldr bldr) {}
|
||||
public void Cmd_end() {}
|
||||
public void Cmd_term() {}
|
||||
public final String Name;
|
||||
public final int[] Db_ids;
|
||||
public boolean Db_ids__has(int id) {return true;}
|
||||
// private static List_adp Fill_tbl_names(List_adp rv, int db_tid) {
|
||||
// switch (db_tid) {
|
||||
// case Xowd_db_file_.Tid_cat:
|
||||
// return
|
||||
// break;
|
||||
// }
|
||||
}
|
||||
@@ -48,7 +48,7 @@ public class Xob_diff_regy_make_cmd extends Xob_itm_basic_base implements Xob_cm
|
||||
Sqlite_engine_.Idx_create(make_db_provider, Xob_diff_regy_tbl.Idx_diff_regy__load);
|
||||
}
|
||||
private void Make_delete_sql(Db_conn make_db_provider) {
|
||||
DataRdr rdr = make_db_provider.Exec_sql_as_rdr(Xob_diff_regy_tbl.Make_deletes);
|
||||
DataRdr rdr = make_db_provider.Exec_sql_as_old_rdr(Xob_diff_regy_tbl.Make_deletes);
|
||||
int cur_db_id = -1, cur_count = 0;
|
||||
Bry_bfr atr_bfr = Bry_bfr.new_(), bin_bfr = Bry_bfr.new_();
|
||||
Io_url sql_tmp_dir = wiki.App().Fsys_mgr().File_dir().GenSubDir_nest(wiki.Domain_str(), "tmp_sql");
|
||||
|
||||
@@ -49,7 +49,7 @@ public class Xob_orig_regy_update_cmd extends Xob_itm_basic_base implements Xob_
|
||||
}
|
||||
*/
|
||||
}
|
||||
public DataRdr Select(Db_conn p, byte prv_repo_id, byte[] prv_ttl) {
|
||||
public DataRdr Select(Db_conn conn, byte prv_repo_id, byte[] prv_ttl) {
|
||||
String sql = String_.Concat_lines_nl_skip_last
|
||||
( "SELECT lnki_ttl"
|
||||
, "FROM orig_regy"
|
||||
@@ -58,7 +58,7 @@ public class Xob_orig_regy_update_cmd extends Xob_itm_basic_base implements Xob_
|
||||
, "AND oimg_orig_page_id = -1;"
|
||||
);
|
||||
Db_qry select_qry = Db_qry_sql.rdr_(sql);
|
||||
return p.Exec_qry_as_rdr(select_qry);
|
||||
return conn.Exec_qry_as_old_rdr(select_qry);
|
||||
}
|
||||
public void Cmd_run() {}
|
||||
public void Cmd_end() {}
|
||||
|
||||
@@ -33,19 +33,19 @@ public class Xob_xfer_regy_tbl {
|
||||
p.Exec_sql(Sql_create_data_thumb);
|
||||
}
|
||||
public static void Create_index(Gfo_usr_dlg usr_dlg, Db_conn p) {Sqlite_engine_.Idx_create(usr_dlg, p, Xob_db_file.Name__file_make, Idx_lnki_page_id, Idx_lnki_ttl);}
|
||||
public static DataRdr Select(Db_conn p, byte repo_id, byte[] ttl, int limit) {
|
||||
public static DataRdr Select(Db_conn conn, byte repo_id, byte[] ttl, int limit) {
|
||||
Db_qry qry = Db_qry_.select_().Cols_all_()
|
||||
.From_(Tbl_name)
|
||||
.Where_(gplx.core.criterias.Criteria_.And_many(Db_crt_.mte_(Fld_orig_repo, repo_id), Db_crt_.mt_(Fld_lnki_ttl, String_.new_u8(ttl)), Db_crt_.eq_(Fld_xfer_status, 0)))
|
||||
.OrderBy_many_(Fld_xfer_status, Fld_orig_repo, Fld_lnki_ttl, Fld_file_w)
|
||||
.Where_(gplx.core.criterias.Criteria_.And_many(Db_crt_.New_mte(Fld_orig_repo, repo_id), Db_crt_.New_mt(Fld_lnki_ttl, String_.new_u8(ttl)), Db_crt_.New_eq(Fld_xfer_status, 0)))
|
||||
.Order_asc_many_(Fld_xfer_status, Fld_orig_repo, Fld_lnki_ttl, Fld_file_w)
|
||||
.Limit_(limit)
|
||||
;
|
||||
return p.Exec_qry_as_rdr(qry);
|
||||
return conn.Exec_qry_as_old_rdr(qry);
|
||||
}
|
||||
public static Db_stmt Select_by_page_id_stmt(Db_conn p) {return p.Stmt_new(Db_qry_sql.rdr_(Sql_select));}
|
||||
public static Db_stmt Select_by_page_id_stmt(Db_conn p) {return p.Stmt_new(Db_qry_sql.rdr_(Sql_select_itm));}
|
||||
public static DataRdr Select_by_page_id(Db_stmt stmt, int page_id, int limit) {return stmt.Val_int(page_id).Val_int(limit).Exec_select();}
|
||||
private static final String
|
||||
Sql_select = String_.Concat_lines_nl
|
||||
Sql_select_itm = String_.Concat_lines_nl
|
||||
( "SELECT *"
|
||||
, "FROM xfer_regy"
|
||||
, "WHERE xfer_status = 0"
|
||||
@@ -59,17 +59,17 @@ public class Xob_xfer_regy_tbl {
|
||||
, "WHERE xfer_status = 0"
|
||||
)
|
||||
;
|
||||
public static DataRdr Select_by_tier_page(Db_conn p, int tier_id, int page_id, int select_interval) {
|
||||
public static DataRdr Select_by_tier_page(Db_conn conn, int tier_id, int page_id, int select_interval) {
|
||||
Db_qry qry = Db_qry_.select_().Cols_all_()
|
||||
.From_(Tbl_name)
|
||||
.Where_(gplx.core.criterias.Criteria_.And_many(Db_crt_.eq_(Fld_xfer_status, 0), Db_crt_.eq_(Fld_lnki_tier_id, tier_id), Db_crt_.mte_(Fld_lnki_page_id, page_id)))
|
||||
.OrderBy_many_(Fld_lnki_tier_id, Fld_lnki_page_id, Fld_lnki_id)
|
||||
.Where_(gplx.core.criterias.Criteria_.And_many(Db_crt_.New_eq(Fld_xfer_status, 0), Db_crt_.New_eq(Fld_lnki_tier_id, tier_id), Db_crt_.New_mte(Fld_lnki_page_id, page_id)))
|
||||
.Order_asc_many_(Fld_lnki_tier_id, Fld_lnki_page_id, Fld_lnki_id)
|
||||
.Limit_(select_interval)
|
||||
;
|
||||
return p.Exec_qry_as_rdr(qry);
|
||||
return conn.Exec_qry_as_old_rdr(qry);
|
||||
}
|
||||
public static int Select_total_pending(Db_conn p) {
|
||||
DataRdr rdr = p.Exec_sql_as_rdr(Sql_select_total_pending);
|
||||
DataRdr rdr = p.Exec_sql_as_old_rdr(Sql_select_total_pending);
|
||||
int rv = 0;
|
||||
if (rdr.MoveNextPeer())
|
||||
rv = rdr.ReadInt("CountAll");
|
||||
|
||||
@@ -30,7 +30,7 @@ public class Xob_xfer_temp_cmd_orig extends Xob_itm_basic_base implements Xob_cm
|
||||
Xob_xfer_temp_tbl.Create_table(conn);
|
||||
Db_stmt trg_stmt = Xob_xfer_temp_tbl.Insert_stmt(conn);
|
||||
conn.Txn_bgn("bldr__xfer_temp");
|
||||
DataRdr rdr = conn.Exec_sql_as_rdr(Sql_select);
|
||||
DataRdr rdr = conn.Exec_sql_as_old_rdr(Sql_select_itm);
|
||||
long[] ext_maxs = Calc_ext_max();
|
||||
while (rdr.MoveNextPeer()) {
|
||||
int lnki_ext = rdr.ReadByte(Xob_lnki_regy_tbl.Fld_lnki_ext);
|
||||
@@ -76,7 +76,7 @@ public class Xob_xfer_temp_cmd_orig extends Xob_itm_basic_base implements Xob_cm
|
||||
public void Cmd_end() {}
|
||||
public void Cmd_term() {}
|
||||
private static final String
|
||||
Sql_select = String_.Concat_lines_nl
|
||||
Sql_select_itm = String_.Concat_lines_nl
|
||||
( "SELECT DISTINCT"
|
||||
, " l.lnki_id"
|
||||
// , ", lnki_ttl"
|
||||
|
||||
@@ -28,7 +28,7 @@ public class Xob_xfer_temp_cmd_thumb extends Xob_itm_basic_base implements Xob_c
|
||||
Xob_xfer_temp_tbl.Create_table(conn);
|
||||
Db_stmt trg_stmt = Xob_xfer_temp_tbl.Insert_stmt(conn);
|
||||
conn.Txn_bgn("bldr__xfer_temp_thumb");
|
||||
DataRdr rdr = conn.Exec_sql_as_rdr(Sql_select);
|
||||
DataRdr rdr = conn.Exec_sql_as_old_rdr(Sql_select_itm);
|
||||
Xob_xfer_temp_itm temp_itm = new Xob_xfer_temp_itm();
|
||||
Xof_img_size img_size = new Xof_img_size();
|
||||
byte[] cur_ttl = Bry_.Empty; byte cur_repo = Byte_.Max_value_127;
|
||||
@@ -52,7 +52,7 @@ public class Xob_xfer_temp_cmd_thumb extends Xob_itm_basic_base implements Xob_c
|
||||
public void Cmd_end() {}
|
||||
public void Cmd_term() {}
|
||||
private static final String
|
||||
Sql_select = String_.Concat_lines_nl
|
||||
Sql_select_itm = String_.Concat_lines_nl
|
||||
( "SELECT l.lnki_id"
|
||||
, ", l.lnki_tier_id"
|
||||
, ", l.lnki_page_id"
|
||||
|
||||
@@ -37,6 +37,7 @@ public class Xob_search_sql_cmd extends Xob_itm_basic_base implements Xob_cmd {
|
||||
Db_conn search_conn = search_db.Conn();
|
||||
Xowd_search_temp_tbl search_temp_tbl = new Xowd_search_temp_tbl(search_conn, db_mgr.Props().Schema_is_1());
|
||||
search_temp_tbl.Create_tbl();
|
||||
search_conn.Exec_delete_all(search_temp_tbl.Tbl_name());
|
||||
search_temp_tbl.Insert_bgn();
|
||||
Xowd_page_tbl page_tbl = db_mgr.Tbl__page();
|
||||
Db_rdr page_rdr = page_tbl.Select_all();
|
||||
|
||||
@@ -22,7 +22,7 @@ import gplx.xowa.langs.*;
|
||||
import gplx.xowa.wikis.data.*; import gplx.dbs.*; import gplx.dbs.engines.sqlite.*; import gplx.xowa.wikis.dbs.*; import gplx.xowa.wikis.data.tbls.*;
|
||||
public class Xob_search_sql_wkr extends Xob_search_base implements Io_make_cmd { // search version 2
|
||||
private Xowd_db_mgr db_mgr; private Xowd_search_link_tbl search_page_tbl; private Xowd_search_word_tbl search_word_tbl;
|
||||
private int search_id = 0; private byte[] prv_word = Bry_.Empty; private int page_count;
|
||||
private int search_id = 0; private byte[] prv_word = null; private int page_count;
|
||||
public Xob_search_sql_wkr(Xob_bldr bldr, Xowe_wiki wiki) {this.Cmd_ctor(bldr, wiki);}
|
||||
@Override public String Wkr_key() {return Xob_cmd_keys.Key_text_search_wkr;}
|
||||
@Override public gplx.core.ios.Io_make_cmd Make_cmd_site() {return this;}
|
||||
@@ -35,20 +35,22 @@ public class Xob_search_sql_wkr extends Xob_search_base implements Io_make_cmd {
|
||||
this.search_word_tbl = db_mgr.Db__search().Tbl__search_word();
|
||||
search_page_tbl.Insert_bgn(); search_word_tbl.Insert_bgn();
|
||||
}
|
||||
public void Sort_do(Io_line_rdr rdr) {
|
||||
byte[] bry = rdr.Bfr();
|
||||
byte[] cur_word = Bry_.Mid(bry, rdr.Key_pos_bgn(), rdr.Key_pos_end());
|
||||
if (!Bry_.Eq(cur_word, prv_word)) {
|
||||
search_word_tbl.Insert_cmd_by_batch(++search_id, prv_word, page_count);
|
||||
public void Sort_do(Io_line_rdr rdr) {Sort_do(rdr.Bfr(), rdr.Key_pos_bgn(), rdr.Key_pos_end());}
|
||||
public void Sort_do(byte[] line, int key_bgn, int key_end) {// EX: abc|123
|
||||
byte[] cur_word = Bry_.Mid(line, key_bgn, key_end);
|
||||
if (!Bry_.Eq(cur_word, prv_word)) { // if new_word, insert old one
|
||||
if (prv_word != null) // do not insert for 1st word
|
||||
search_word_tbl.Insert_cmd_by_batch(search_id, prv_word, page_count);
|
||||
++search_id;
|
||||
prv_word = cur_word;
|
||||
page_count = 0;
|
||||
}
|
||||
search_page_tbl.Insert_cmd_by_batch(search_id, Base85_.To_int_by_bry(bry, rdr.Key_pos_end() + 1, rdr.Key_pos_end() + 5)); // -1: ignore rdr_dlm
|
||||
search_page_tbl.Insert_cmd_by_batch(search_id, Base85_.To_int_by_bry(line, key_end + 1, key_end + 5)); // -1: ignore rdr_dlm
|
||||
++page_count;
|
||||
if (search_id % 10000 == 0)
|
||||
usr_dlg.Prog_many("", "", "creating title index: count=~{0}", search_id);
|
||||
if (search_id % 10000 == 0) usr_dlg.Prog_many("", "", "creating title index: count=~{0}", search_id);
|
||||
}
|
||||
public void Sort_end() {
|
||||
search_word_tbl.Insert_cmd_by_batch(search_id, prv_word, page_count);
|
||||
search_page_tbl.Insert_end(); search_word_tbl.Insert_end();
|
||||
Xowd_db_file search_db = db_mgr.Db__search();
|
||||
Xowd_search_temp_tbl search_temp_tbl = new Xowd_search_temp_tbl(search_db.Conn(), db_mgr.Props().Schema_is_1());
|
||||
|
||||
@@ -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.bldrs.cmds.texts.sqls; import gplx.*; import gplx.xowa.*; import gplx.xowa.bldrs.*; import gplx.xowa.bldrs.cmds.*; import gplx.xowa.bldrs.cmds.texts.*;
|
||||
import org.junit.*; import gplx.dbs.*; import gplx.xowa.wikis.data.tbls.*;
|
||||
public class Xob_search_sql_wkr_tst {
|
||||
private final Xob_search_sql_wkr_fxt fxt = new Xob_search_sql_wkr_fxt();
|
||||
@Test public void Basic() {
|
||||
fxt.Exec__sort
|
||||
( "a|!!!!#"
|
||||
, "a|!!!!$"
|
||||
, "b|!!!!#"
|
||||
, "b|!!!!$"
|
||||
, "b|!!!!%"
|
||||
);
|
||||
fxt.Test__search_word
|
||||
( "1|a|2"
|
||||
, "2|b|3"
|
||||
);
|
||||
fxt.Test__search_link
|
||||
( "1|2"
|
||||
, "1|3"
|
||||
, "2|2"
|
||||
, "2|3"
|
||||
, "2|4"
|
||||
);
|
||||
}
|
||||
}
|
||||
class Xob_search_sql_wkr_fxt {
|
||||
private final Xob_search_sql_wkr wkr;
|
||||
private final Xowe_wiki wiki;
|
||||
private final Bry_bfr tmp_bfr = Bry_bfr.new_();
|
||||
public Xob_search_sql_wkr_fxt() {
|
||||
Xoae_app app = Xoa_app_fxt.app_();
|
||||
this.wiki = Xoa_app_fxt.wiki_tst_(app);
|
||||
Xoa_test_.Db__init__mem(wiki);
|
||||
wkr = new Xob_search_sql_wkr(app.Bldr(), wiki);
|
||||
}
|
||||
public void Exec__sort(String... lines_str) {
|
||||
byte[][] lines = Bry_.Ary(lines_str);
|
||||
wkr.Sort_bgn();
|
||||
for (byte[] line : lines)
|
||||
wkr.Sort_do(line, 0, Bry_find_.Find_fwd(line, Byte_ascii.Pipe));
|
||||
wkr.Sort_end();
|
||||
}
|
||||
public void Test__search_word(String... lines) {
|
||||
Xowd_search_word_tbl tbl = wiki.Data__core_mgr().Db__search().Tbl__search_word();
|
||||
Tfds.Eq_str_lines(String_.Concat_lines_nl(lines), Xoa_test_.Db__print_tbl_as_str(tmp_bfr, tbl.conn, tbl.Tbl_name(), tbl.Fld_id(), tbl.Fld_text(), tbl.Fld_page_count()));
|
||||
}
|
||||
public void Test__search_link(String... lines) {
|
||||
Xowd_search_link_tbl tbl = wiki.Data__core_mgr().Db__search().Tbl__search_link();
|
||||
Tfds.Eq_str_lines(String_.Concat_lines_nl(lines), Xoa_test_.Db__print_tbl_as_str(tmp_bfr, tbl.conn, tbl.Tbl_name(), tbl.Fld_word_id(), tbl.Fld_page_id()));
|
||||
}
|
||||
}
|
||||
@@ -41,19 +41,19 @@ public class Xod_app {
|
||||
Xoa_url url = wiki.Utl__url_parser().Parse(random_ttl_bry);
|
||||
return Wiki__get_by_url(wiki, url);
|
||||
}
|
||||
public String[] Wiki__search(Cancelable cancelable, Xow_wiki wiki, Xows_ui_async ui_async, String search) {
|
||||
Xows_db_wkr search_wkr = new Xows_db_wkr();
|
||||
Xows_db_row[] rows = search_wkr.Search_by_drd(cancelable, wiki, ui_async, Bry_.new_u8(search), 50);
|
||||
int len = rows.length;
|
||||
String[] rv = new String[len];
|
||||
for (int i = 0; i < len; ++i) {
|
||||
rv[i] = String_.new_u8(rows[i].Page_ttl().Page_txt());
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
public void Wiki__search(Cancelable cancelable, Xow_wiki wiki, Xows_ui_async ui_async, String search, Xod_search_cmd[] cmds) {
|
||||
// public String[] Wiki__search(Cancelable cancelable, Srch_rslt_lnr rslt_lnr, Xow_wiki wiki, String search) {
|
||||
// Srch_db_wkr search_wkr = new Srch_db_wkr();
|
||||
// Srch_rslt_itm[] rows = search_wkr.Search_by_drd(cancelable, wiki, ui_async, Bry_.new_u8(search), 50);
|
||||
// int len = rows.length;
|
||||
// String[] rv = new String[len];
|
||||
// for (int i = 0; i < len; ++i) {
|
||||
// rv[i] = String_.new_u8(rows[i].page_ttl.Page_txt());
|
||||
// }
|
||||
// return rv;
|
||||
// }
|
||||
public void Wiki__search(Cancelable cancelable, Srch_rslt_lnr rslt_lnr, Xow_wiki wiki, String search, Xod_search_cmd[] cmds) {
|
||||
for (Xod_search_cmd cmd : cmds)
|
||||
cmd.Search(cancelable, wiki, ui_async, search);
|
||||
cmd.Search(cancelable, rslt_lnr, wiki, search);
|
||||
}
|
||||
public void Page__load_files(Xow_wiki wiki, Xod_page_itm pg, Xog_js_wkr js_wkr) {
|
||||
file_mgr.Load_files(wiki, pg, js_wkr);
|
||||
|
||||
@@ -18,5 +18,5 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
package gplx.xowa.drds; import gplx.*; import gplx.xowa.*;
|
||||
import gplx.xowa.specials.search.*;
|
||||
public interface Xod_search_cmd {
|
||||
void Search(Cancelable cancelable, Xow_wiki wiki, Xows_ui_async ui_async, String search);
|
||||
void Search(Cancelable cancelable, Srch_rslt_lnr rslt_lnr, Xow_wiki wiki, String search);
|
||||
}
|
||||
|
||||
@@ -27,24 +27,24 @@ public class Xod_search_cmd_ {
|
||||
;
|
||||
}
|
||||
class Xod_search_cmd__page_eq implements Xod_search_cmd {
|
||||
public void Search(Cancelable cancelable, Xow_wiki wiki, Xows_ui_async ui_async, String search) {
|
||||
public void Search(Cancelable cancelable, Srch_rslt_lnr rslt_lnr, Xow_wiki wiki, String search) {
|
||||
Xowd_page_itm page_itm = new Xowd_page_itm();
|
||||
if (wiki.Data__core_mgr().Tbl__page().Select_by_ttl(page_itm, wiki.Ns_mgr().Ns_main(), Bry_.Ucase__1st(Bry_.new_u8(search)))) {
|
||||
Xows_db_row search_itm = new Xows_db_row(wiki.Domain_bry(), wiki.Ttl_parse(page_itm.Ttl_page_db()), page_itm.Id(), page_itm.Text_len());
|
||||
ui_async.Add(search_itm);
|
||||
Srch_rslt_itm search_itm = new Srch_rslt_itm(wiki.Domain_bry(), wiki.Ttl_parse(page_itm.Ttl_page_db()), page_itm.Id(), page_itm.Text_len());
|
||||
rslt_lnr.Notify_rslt_found(search_itm);
|
||||
}
|
||||
}
|
||||
public static final Xod_search_cmd__page_eq Instance = new Xod_search_cmd__page_eq(); Xod_search_cmd__page_eq() {}
|
||||
}
|
||||
class Xod_search_cmd__page_like implements Xod_search_cmd {// NOTE: slow; takes at least 10+ seconds
|
||||
public void Search(Cancelable cancelable, Xow_wiki wiki, Xows_ui_async ui_async, String search) {
|
||||
public void Search(Cancelable cancelable, Srch_rslt_lnr rslt_lnr, Xow_wiki wiki, String search) {
|
||||
List_adp tmp_list = List_adp_.new_();
|
||||
wiki.Data__core_mgr().Tbl__page().Select_by_search(cancelable, tmp_list, Bry_.Ucase__1st(Bry_.new_u8(search + "*")), 50);
|
||||
int len = tmp_list.Count();
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Xowd_page_itm page_itm = (Xowd_page_itm)tmp_list.Get_at(i);
|
||||
Xows_db_row search_itm = new Xows_db_row(wiki.Domain_bry(), wiki.Ttl_parse(page_itm.Ttl_page_db()), page_itm.Id(), page_itm.Text_len());
|
||||
ui_async.Add(search_itm);
|
||||
Srch_rslt_itm search_itm = new Srch_rslt_itm(wiki.Domain_bry(), wiki.Ttl_parse(page_itm.Ttl_page_db()), page_itm.Id(), page_itm.Text_len());
|
||||
rslt_lnr.Notify_rslt_found(search_itm);
|
||||
}
|
||||
}
|
||||
public static final Xod_search_cmd__page_like Instance = new Xod_search_cmd__page_like(); Xod_search_cmd__page_like() {}
|
||||
@@ -52,10 +52,10 @@ class Xod_search_cmd__page_like implements Xod_search_cmd {// NOTE: slow; takes
|
||||
class Xod_search_cmd__word_tbl implements Xod_search_cmd {
|
||||
private final boolean wildcard;
|
||||
private final int results_wanted;
|
||||
private final Xows_db_wkr search_wkr = new Xows_db_wkr();
|
||||
private final Srch_db_wkr search_wkr = new Srch_db_wkr();
|
||||
Xod_search_cmd__word_tbl(boolean wildcard, int results_wanted) {this.wildcard = wildcard; this.results_wanted = results_wanted;}
|
||||
public void Search(Cancelable cancelable, Xow_wiki wiki, Xows_ui_async ui_async, String search) {
|
||||
search_wkr.Search_by_drd(cancelable, wiki, ui_async, Bry_.new_u8(Standardize_search(search, wildcard)), results_wanted);
|
||||
public void Search(Cancelable cancelable, Srch_rslt_lnr rslt_lnr, Xow_wiki wiki, String search) {
|
||||
search_wkr.Search_by_drd(cancelable, rslt_lnr, wiki, Bry_.new_u8(Standardize_search(search, wildcard)), results_wanted);
|
||||
}
|
||||
public static final Xod_search_cmd__word_tbl Instance_eq = new Xod_search_cmd__word_tbl(Bool_.N, 10), Instance_like = new Xod_search_cmd__word_tbl(Bool_.Y, 50);
|
||||
private static String Standardize_search(String search, boolean wildcard) {
|
||||
|
||||
@@ -95,7 +95,7 @@ class Xof_orig_tbl__in_wkr extends Db_in_wkr__base {
|
||||
public Xof_orig_tbl__in_wkr Init(Ordered_hash rv, List_adp itms) {this.itms = itms; this.rv = rv; return this;}
|
||||
@Override protected Db_qry Make_qry(int bgn, int end) {
|
||||
Object[] part_ary = In_ary(end - bgn);
|
||||
return Db_qry_.select_cols_(tbl_name, Db_crt_.in_(fld_ttl, part_ary), flds.To_str_ary());
|
||||
return Db_qry_.select_cols_(tbl_name, Db_crt_.New_in(fld_ttl, part_ary), flds.To_str_ary());
|
||||
}
|
||||
@Override protected void Fill_stmt(Db_stmt stmt, int bgn, int end) {
|
||||
for (int i = bgn; i < end; i++) {
|
||||
|
||||
@@ -31,7 +31,7 @@ class Xob_hdump_img_cmd extends Xob_itm_basic_base implements Xob_cmd {
|
||||
private void Exec_main() {
|
||||
Bry_bfr bfr = Bry_bfr.reset_(Io_mgr.Len_mb);
|
||||
Db_conn conn = Xob_db_file.new__file_make(wiki.Fsys_mgr().Root_dir()).Conn();
|
||||
Db_rdr rdr = conn.Stmt_new(gplx.dbs.qrys.Db_qry_sql.rdr_(Sql_select)).Exec_select__rls_auto();
|
||||
Db_rdr rdr = conn.Stmt_new(gplx.dbs.qrys.Db_qry_sql.rdr_(Sql_select_itm)).Exec_select__rls_auto();
|
||||
// html_tbl = new Xowd_html_tbl(conn, wiki.Db_mgr_as_sql().Core_data_mgr().Props().Zip_tid_text());
|
||||
int cur_page_id = -1;
|
||||
while (rdr.Move_next()) {
|
||||
@@ -57,7 +57,7 @@ class Xob_hdump_img_cmd extends Xob_itm_basic_base implements Xob_cmd {
|
||||
if (page_id == -1 || data.length == 0) return;
|
||||
// html_tbl.Insert(page_id, Xohd_img_tid.Tid_img, data);
|
||||
}
|
||||
private static final String Sql_select = String_.Concat_lines_nl_skip_last
|
||||
private static final String Sql_select_itm = String_.Concat_lines_nl_skip_last
|
||||
( "SELECT lt.lnki_page_id"
|
||||
, ", lt.html_uid"
|
||||
, ", lt.lnki_ttl"
|
||||
|
||||
@@ -35,7 +35,7 @@ public class Xob_redlink_mkr_cmd extends Xob_itm_basic_base implements Xob_cmd {
|
||||
Xowd_page_tbl page_tbl = core_db.Tbl__page();
|
||||
int cur_html_db_id = -1, cur_page_id = -1;
|
||||
Xoh_redlink_tbl redlink_tbl = new Xoh_redlink_tbl(page_tbl.Conn());
|
||||
Db_rdr rdr = attach_rdr.Exec_as_rdr(Sql_select);
|
||||
Db_rdr rdr = attach_rdr.Exec_as_rdr(Sql_select_itm);
|
||||
try {
|
||||
while (rdr.Move_next()) {
|
||||
// switch html_db if needed
|
||||
@@ -69,7 +69,7 @@ public class Xob_redlink_mkr_cmd extends Xob_itm_basic_base implements Xob_cmd {
|
||||
if ((commit_count % commit_interval ) == 0)
|
||||
redlink_tbl.Conn().Txn_sav();
|
||||
}
|
||||
private static final String Sql_select = String_.Concat_lines_nl_skip_last
|
||||
private static final String Sql_select_itm = String_.Concat_lines_nl_skip_last
|
||||
( "SELECT p.page_html_db_id"
|
||||
, ", p.page_id"
|
||||
, ", ld.src_html_uid"
|
||||
|
||||
@@ -38,7 +38,7 @@ public class Xoh_file_html_fmtr__hdump extends Xoh_file_html_fmtr__base {
|
||||
, Gfh_utl.Escape_html_as_bry(img_alt), data_xowa_title, data_xowa_image, arg_img_core.Init(uid, Bry_.Empty, 0, 0), Xoh_img_cls_.To_html(img_cls, img_cls_other));
|
||||
}
|
||||
public static void Bld_anch_n(Bry_bfr bfr, byte[] data_xowa_title, byte[] data_xowa_image, byte img_cls, byte[] img_cls_other, byte[] img_alt, byte[] img_xtra_atrs) {
|
||||
fmtr_anch_n.Bld_bfr_many(bfr, data_xowa_title, data_xowa_image, Xoh_img_cls_.To_html(img_cls, img_cls_other), Gfh_utl.Escape_html_as_bry(img_alt), img_xtra_atrs);
|
||||
fmtr_anch_n.Bld_many(bfr, data_xowa_title, data_xowa_image, Xoh_img_cls_.To_html(img_cls, img_cls_other), Gfh_utl.Escape_html_as_bry(img_alt), img_xtra_atrs);
|
||||
}
|
||||
public static byte[] Bld_xowa_image_data(Bry_bfr tmp_bfr, byte tid, int w, int h, double upright, double time, int page) {
|
||||
tmp_bfr.Add_byte_space().Add(Xoh_img_xoimg_data.Bry__data_xowa_image).Add_byte_eq().Add_byte_quote();
|
||||
|
||||
@@ -311,7 +311,7 @@ public class Xoh_thm_hzip_tst {
|
||||
fxt.Wiki().Ns_mgr().Init();
|
||||
|
||||
fxt.Init_mode_is_b256_(Bool_.N);
|
||||
fxt.Exec_write_to_fsys(Io_url_.new_dir_("J:\\xowa\\dev_rls\\html\\"), "debug.html");
|
||||
fxt.Exec_write_to_fsys(Io_url_.new_dir_("J:\\xowa\\research\\html\\"), "debug.html");
|
||||
fxt.Init_mode_is_b256_(Bool_.N);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,8 +17,9 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.specials.randoms; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
public class Rndm_core_row {
|
||||
public Rndm_core_row(int type, int total, int interval) {this.type = type; this.total = total; this.interval = interval;}
|
||||
public final int type;
|
||||
public final int total;
|
||||
public final int interval;
|
||||
public void Load(int uid, String where_sql, int total, int interval) {this.uid = uid; this.where_sql = where_sql; this.total = total; this.interval = interval;}
|
||||
public int uid;
|
||||
public String where_sql;
|
||||
public int total;
|
||||
public int interval;
|
||||
}
|
||||
|
||||
@@ -19,31 +19,34 @@ package gplx.xowa.specials.randoms; import gplx.*; import gplx.xowa.*; import gp
|
||||
import gplx.core.ios.*; import gplx.dbs.*; import gplx.dbs.utls.*;
|
||||
public class Rndm_core_tbl implements Rls_able {
|
||||
private final String tbl_name = "rndm_core"; private final Dbmeta_fld_list flds = Dbmeta_fld_list.new_();
|
||||
private final String fld_rndm_uid, fld_rndm_total, fld_rndm_interval;
|
||||
private final Db_conn conn; private Db_stmt stmt_select, stmt_insert;
|
||||
private final String fld_uid, fld_where_sql, fld_total, fld_interval;
|
||||
private final Db_conn conn; private Db_stmt stmt_select;
|
||||
public Rndm_core_tbl(Db_conn conn) {
|
||||
this.conn = conn;
|
||||
fld_rndm_uid = flds.Add_int("rndm_uid");
|
||||
fld_rndm_total = flds.Add_int("rndm_total");
|
||||
fld_rndm_interval = flds.Add_int("rndm_interval");
|
||||
fld_uid = flds.Add_int_pkey("rndm_uid");
|
||||
fld_where_sql = flds.Add_str("rndm_where_sql", 1024);
|
||||
fld_total = flds.Add_int("rndm_total");
|
||||
fld_interval = flds.Add_int("rndm_interval");
|
||||
conn.Rls_reg(this);
|
||||
}
|
||||
public void Create_tbl() {conn.Ddl_create_tbl(Dbmeta_tbl_itm.New(tbl_name, flds, Dbmeta_idx_itm.new_unique_by_name(tbl_name, "core", fld_rndm_uid)));}
|
||||
public void Insert(int uid, int total, int interval) {
|
||||
if (stmt_insert == null) stmt_insert = conn.Stmt_insert(tbl_name, flds);
|
||||
stmt_insert.Clear().Val_int(fld_rndm_uid, uid).Val_int(fld_rndm_total, total).Val_int(interval).Exec_insert();
|
||||
public void Create_tbl() {conn.Ddl_create_tbl(Dbmeta_tbl_itm.New(tbl_name, flds, Dbmeta_idx_itm.new_unique_by_name(tbl_name, "core", fld_uid)));}
|
||||
public void Upsert(int uid, String where_sql, int total, int interval) {
|
||||
conn.Stmt_delete(tbl_name, fld_uid).Crt_int(fld_uid, uid).Exec_delete();
|
||||
conn.Stmt_insert(tbl_name, flds).Val_int(fld_uid, uid).Val_str(fld_where_sql, where_sql).Val_int(fld_total, total).Val_int(fld_interval, interval).Exec_insert();
|
||||
}
|
||||
public Rndm_core_row Select(int uid) {
|
||||
if (stmt_select == null) stmt_select = conn.Stmt_select(tbl_name, flds, fld_rndm_uid);
|
||||
Db_rdr rdr = stmt_select.Clear().Val_int(fld_rndm_uid, uid).Exec_select__rls_manual();
|
||||
public void Select(Rndm_core_row rv, int uid) {
|
||||
if (stmt_select == null) stmt_select = conn.Stmt_select(tbl_name, flds, fld_uid);
|
||||
Db_rdr rdr = stmt_select.Clear().Val_int(fld_uid, uid).Exec_select__rls_manual();
|
||||
try {
|
||||
int total = rdr.Read_int(fld_rndm_total);
|
||||
int interval = rdr.Read_int(fld_rndm_interval);
|
||||
return new Rndm_core_row(uid, total, interval);
|
||||
if (rdr.Move_next()) {
|
||||
String where_sql = rdr.Read_str(fld_where_sql);
|
||||
int total = rdr.Read_int(fld_total);
|
||||
int interval = rdr.Read_int(fld_interval);
|
||||
rv.Load(uid, where_sql, total, interval);
|
||||
}
|
||||
} finally {rdr.Rls();}
|
||||
}
|
||||
public void Rls() {
|
||||
stmt_select = Db_stmt_.Rls(stmt_select);
|
||||
stmt_insert = Db_stmt_.Rls(stmt_insert);
|
||||
}
|
||||
}
|
||||
|
||||
90
400_xowa/src/gplx/xowa/specials/randoms/Rndm_mgr.java
Normal file
90
400_xowa/src/gplx/xowa/specials/randoms/Rndm_mgr.java
Normal file
@@ -0,0 +1,90 @@
|
||||
/*
|
||||
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.specials.randoms; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.core.primitives.*; import gplx.core.brys.fmtrs.*;
|
||||
import gplx.dbs.*; import gplx.xowa.wikis.data.tbls.*;
|
||||
public class Rndm_mgr implements Rls_able {
|
||||
private Rndm_core_tbl core_tbl; private final Rndm_core_row core_row = new Rndm_core_row();
|
||||
private Rndm_range_tbl rng_tbl;
|
||||
private Xowd_page_tbl page_tbl; private Db_stmt stmt__page__random;
|
||||
public void Init(Db_conn conn, Xowd_page_tbl page_tbl) {
|
||||
core_tbl = new Rndm_core_tbl(conn);
|
||||
rng_tbl = new Rndm_range_tbl(conn);
|
||||
this.page_tbl = page_tbl;
|
||||
conn.Rls_reg(this);
|
||||
}
|
||||
public void Rebuild(int uid, String where_sql, int interval) {
|
||||
int total_count = 0; List_adp rng_list = List_adp_.new_();
|
||||
Db_conn conn = page_tbl.Conn();
|
||||
Db_stmt stmt = conn.Stmt_select_order(page_tbl.Tbl_name(), String_.Ary(page_tbl.Fld_page_id()), String_.Ary_empty, page_tbl.Fld_page_id());
|
||||
Db_rdr rdr = stmt.Exec_select__rls_auto();
|
||||
try {
|
||||
while (rdr.Move_next()) {
|
||||
++total_count; // add to total count first so (total_count % interval) is never 0 for total_count = 0
|
||||
if (total_count % interval == 0) {
|
||||
int cur_page_id = rdr.Read_int(page_tbl.Fld_page_id());
|
||||
rng_list.Add(Int_obj_ref.new_(cur_page_id));
|
||||
}
|
||||
}
|
||||
}
|
||||
finally {rdr.Rls();}
|
||||
conn.Txn_bgn("rndm_rebuild");
|
||||
core_tbl.Upsert(uid, where_sql, total_count, interval);
|
||||
int rng_ary_len = rng_list.Count();
|
||||
rng_tbl.Insert_bgn(uid);
|
||||
for (int i = 0; i < rng_ary_len; ++i) {
|
||||
Int_obj_ref rng_itm = (Int_obj_ref)rng_list.Get_at(i);
|
||||
rng_tbl.Insert_itm(uid, i + 1, rng_itm.Val());
|
||||
}
|
||||
rng_tbl.Insert_end();
|
||||
conn.Txn_end();
|
||||
}
|
||||
public int Get_rndm_page(int uid) { // EX: ns=0;type_is_redirect=0
|
||||
synchronized (core_row) {core_tbl.Select(core_row, uid);}
|
||||
int rndm_num = RandomAdp_.new_().Next(core_row.total);
|
||||
int rng_idx = rndm_num / core_row.interval;
|
||||
int itm_idx = rndm_num % core_row.interval;
|
||||
int page_id_bgn = rng_idx == 0 ? 0 : rng_tbl.Select_or_neg_1(uid, rng_idx);
|
||||
int rv = Select_by_offset(core_row.where_sql, page_id_bgn, itm_idx);
|
||||
return rv;
|
||||
}
|
||||
private int Select_by_offset(String where_sql, int page_id_bgn, int offset) {
|
||||
Bry_bfr bfr = Bry_bfr.new_();
|
||||
where_sql = fmt_where.Fmt_(where_sql).Bld_many_to_str(bfr, page_tbl.Fld_page_ns(), page_tbl.Fld_is_redirect());
|
||||
String sql = fmt_sql.Bld_many_to_str(bfr, page_tbl.Tbl_name(), page_tbl.Fld_page_id(), where_sql, page_id_bgn, offset);
|
||||
Db_rdr rdr = Db_rdr_.Empty;
|
||||
try {
|
||||
rdr = page_tbl.Conn().Exec_sql_as_rdr_v2(sql);
|
||||
return rdr.Move_next() ? rdr.Read_int(page_tbl.Fld_page_id()) : -1;
|
||||
}
|
||||
finally {rdr.Rls();}
|
||||
}
|
||||
public void Rls() {
|
||||
stmt__page__random = Db_stmt_.Rls(stmt__page__random);
|
||||
}
|
||||
private static final Bry_fmt fmt_sql = Bry_fmt.New(String_.Concat_lines_nl_skip_last
|
||||
( "SELECT p.~{page_id}"
|
||||
, "FROM ~{page} p"
|
||||
, "WHERE p.~{~page_id} > ~{page_id_bgn}"
|
||||
, "~{where_sql}"
|
||||
, "ORDER BY ~{page_id}"
|
||||
, "LIMIT 1"
|
||||
, "OFFSET ~{offset};"
|
||||
), "page", "page_id", "where_sql", "page_id_bgn", "offset");
|
||||
private static final Bry_fmt fmt_where = Bry_fmt.New("", "page_namespace", "page_is_redirect");
|
||||
}
|
||||
@@ -29,29 +29,24 @@ public class Rndm_range_tbl implements Rls_able {
|
||||
conn.Rls_reg(this);
|
||||
}
|
||||
public void Create_tbl() {conn.Ddl_create_tbl(Dbmeta_tbl_itm.New(tbl_name, flds, Dbmeta_idx_itm.new_unique_by_name(tbl_name, "core", fld_rng_uid, fld_rng_idx)));}
|
||||
public void Insert(int uid, int idx, int page_id) {
|
||||
if (stmt_insert == null) stmt_insert = conn.Stmt_insert(tbl_name, flds);
|
||||
public void Insert_bgn(int uid) {
|
||||
conn.Stmt_delete(tbl_name, fld_rng_uid).Crt_int(fld_rng_uid, uid).Exec_delete();
|
||||
stmt_insert = conn.Stmt_insert(tbl_name, flds);
|
||||
}
|
||||
public void Insert_itm(int uid, int idx, int page_id) {
|
||||
stmt_insert.Clear().Val_int(fld_rng_uid, uid).Val_int(fld_rng_idx, idx).Val_int(fld_rng_page_id, page_id).Exec_insert();
|
||||
}
|
||||
public void Select(int type) {
|
||||
// if (stmt_select == null) stmt_select = conn.Stmt_select(tbl_name, flds, fld_rng_uid);
|
||||
// Db_rdr rdr = stmt_select.Clear().Val_int(fld_rng_type, type).Exec_select__rls_manual();
|
||||
// try {
|
||||
// int total = rdr.Read_int(fld_rng_total);
|
||||
// int interval = rdr.Read_int(fld_rng_interval);
|
||||
// return new Rndm_core_row(type, total, interval);
|
||||
// } finally {rdr.Rls();}
|
||||
public void Insert_end() {
|
||||
stmt_insert = Db_stmt_.Rls(stmt_insert);
|
||||
}
|
||||
public int Select_or_neg_1(int core_uid, int rng_idx) {
|
||||
if (stmt_select == null) stmt_select = conn.Stmt_select(tbl_name, flds, fld_rng_uid, fld_rng_idx);
|
||||
Db_rdr rdr = stmt_select.Clear().Val_int(fld_rng_uid, core_uid).Val_int(fld_rng_idx, rng_idx).Exec_select__rls_manual();
|
||||
try {return rdr.Move_next() ? rdr.Read_int(fld_rng_page_id) : -1;}
|
||||
catch (Exception e) {Gfo_usr_dlg_.Instance.Warn_many("", "", "failed to get rndm_idx; url=~{0} core_uid=~{1} rng_idx=~{2} err=~{3}", conn.Conn_info().Xto_api(), core_uid, rng_idx, Err_.Message_gplx_log(e)); return -1;}
|
||||
finally {rdr.Rls();}
|
||||
}
|
||||
public void Rls() {
|
||||
stmt_select = Db_stmt_.Rls(stmt_select);
|
||||
stmt_insert = Db_stmt_.Rls(stmt_insert);
|
||||
}
|
||||
public void Get_random(int uid) {
|
||||
// Rndm_core_row core_row = core_tbl.Get(uid);
|
||||
// int rnd = RandomAdp_.new_().Next(core_row.total);
|
||||
// int idx = rnd / core_row.interval;
|
||||
// int off = rnd % core_row.interval;
|
||||
// Rndm_rng_row rng_row = rng_tbl.Get(uid, idx);
|
||||
// Xowd_page page = page_tbl.Get_by_page_offset(rng_row.page_id_bgn, off);
|
||||
}
|
||||
}
|
||||
|
||||
40
400_xowa/src/gplx/xowa/specials/randoms/Xob_rnd_cmd.java
Normal file
40
400_xowa/src/gplx/xowa/specials/randoms/Xob_rnd_cmd.java
Normal file
@@ -0,0 +1,40 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.specials.randoms; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.xowa.bldrs.*;
|
||||
public class Xob_rnd_cmd implements Xob_cmd {
|
||||
private final Xowe_wiki wiki;
|
||||
private int rndm_uid = 0; private String rndm_where_sql = "AND ~{page_namespace} = 0 AND ~{page_is_redirect} = 0"; private int rndm_interval = 1000;
|
||||
public Xob_rnd_cmd(Xob_bldr bldr, Xowe_wiki wiki) {this.wiki = wiki;}
|
||||
public String Cmd_key() {return Xob_cmd_keys.Key_util_random;}
|
||||
public void Cmd_run() {
|
||||
wiki.Special_mgr().Page_random().Mgr().Rebuild(rndm_uid, rndm_where_sql, rndm_interval);
|
||||
}
|
||||
public Object Invk(GfsCtx ctx, int ikey, String k, GfoMsg m) {
|
||||
if (ctx.Match(k, Invk_rndm_uid_)) rndm_uid = m.ReadInt("v");
|
||||
else if (ctx.Match(k, Invk_rndm_where_sql_)) rndm_where_sql = m.ReadStr("v");
|
||||
else if (ctx.Match(k, Invk_rndm_interval_)) rndm_interval = m.ReadInt("v");
|
||||
else return GfoInvkAble_.Rv_unhandled;
|
||||
return this;
|
||||
} private static final String Invk_rndm_uid_ = "rndm_uid_", Invk_rndm_where_sql_ = "rndm_where_sql_", Invk_rndm_interval_ = "rndm_interval_";
|
||||
|
||||
public void Cmd_init(Xob_bldr bldr) {}
|
||||
public void Cmd_bgn(Xob_bldr bldr) {}
|
||||
public void Cmd_end() {}
|
||||
public void Cmd_term() {}
|
||||
}
|
||||
@@ -19,6 +19,7 @@ package gplx.xowa.specials.randoms; import gplx.*; import gplx.xowa.*; import gp
|
||||
import gplx.xowa.wikis.nss.*;
|
||||
public class Xows_page_random implements Xows_page {
|
||||
public Xows_page_random(Xowe_wiki wiki) {}
|
||||
public Rndm_mgr Mgr() {return mgr;} private final Rndm_mgr mgr = new Rndm_mgr();
|
||||
public Xows_special_meta Special_meta() {return Xows_special_meta_.Itm__random;}
|
||||
public void Special_gen(Xowe_wiki wiki, Xoae_page page, Xoa_url url, Xoa_ttl ttl) {
|
||||
Xow_ns ns = wiki.Ns_mgr().Names_get_or_main(ttl.Rest_txt());
|
||||
|
||||
130
400_xowa/src/gplx/xowa/specials/search/Srch_db_wkr.java
Normal file
130
400_xowa/src/gplx/xowa/specials/search/Srch_db_wkr.java
Normal file
@@ -0,0 +1,130 @@
|
||||
/*
|
||||
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.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.core.primitives.*; import gplx.core.brys.fmtrs.*;
|
||||
import gplx.dbs.*; import gplx.xowa.wikis.data.*; import gplx.xowa.wikis.data.tbls.*;
|
||||
import gplx.xowa.wikis.nss.*; import gplx.xowa.langs.cases.*;
|
||||
import gplx.xowa.specials.search.crts.*;
|
||||
public class Srch_db_wkr {
|
||||
private Xol_case_mgr drd_case_mgr;
|
||||
public Srch_rslt_itm[] Search_by_drd(Cancelable cxl, Srch_rslt_lnr rslt_lnr, Xow_wiki wiki, byte[] search, int search_results_max) {
|
||||
Xows_ns_mgr ns_mgr = new Xows_ns_mgr(); ns_mgr.Add_main_if_empty();
|
||||
Srch_qry qry = new Srch_qry(search, 0, search_results_max, ns_mgr, Bool_.Y, new gplx.xowa.wikis.domains.Xow_domain_itm[] {wiki.Domain_itm()});
|
||||
Srch_rslt_hash cache = new Srch_rslt_hash(); cache.Init_by_db(cxl, search, wiki.Data__core_mgr().Db__search().Tbl__search_word());
|
||||
if (drd_case_mgr == null) drd_case_mgr = Xol_case_mgr_.U8();
|
||||
Search(cxl, rslt_lnr, cache, wiki, drd_case_mgr, qry);
|
||||
int len = cache.Count();
|
||||
Srch_rslt_itm[] rv = new Srch_rslt_itm[len];
|
||||
for (int i = 0; i < len; ++i)
|
||||
rv[i] = cache.Get_at(i);
|
||||
return rv;
|
||||
}
|
||||
@gplx.Internal protected void Search(Cancelable cxl, Srch_rslt_lnr rslt_lnr, Srch_rslt_hash cache, Xow_wiki wiki, Xol_case_mgr case_mgr, Srch_qry qry) {
|
||||
// get search_words
|
||||
Xowd_db_file search_db = wiki.Data__core_mgr().Db__search();
|
||||
Xoa_app_.Usr_dlg().Prog_many("", "", "search started (please wait)");
|
||||
Srch_crt_node ttl_matcher = cache.Ttl_matcher();
|
||||
if (ttl_matcher == null) {
|
||||
cache.Init_by_db(cxl, case_mgr.Case_build_lower(qry.search_raw), search_db.Tbl__search_word()); // lower-case search
|
||||
ttl_matcher = cache.Ttl_matcher();
|
||||
}
|
||||
// do some init
|
||||
int rslts_wanted = qry.itms_end - qry.itms_bgn;
|
||||
Xowd_db_file core_db = wiki.Data__core_mgr().Db__core();
|
||||
Xowd_page_tbl page_tbl = core_db.Tbl__page();
|
||||
Xowd_search_link_tbl link_tbl = search_db.Tbl__search_link();
|
||||
Srch_word_row[] word_ary = cache.Words(); int word_ary_len = word_ary.length;
|
||||
// read pages for each word from db
|
||||
Db_attach_rdr attach_rdr = new Db_attach_rdr(search_db.Conn(), "page_db", core_db.Url());
|
||||
attach_rdr.Attach();
|
||||
int total_found = 0;
|
||||
try {
|
||||
while (true) {
|
||||
boolean found_none = true;
|
||||
for (int i = 0; i < word_ary_len; ++i) { // loop each word to get rslts_wanted
|
||||
if (cxl.Canceled()) return;
|
||||
Srch_word_row word = word_ary[i];
|
||||
if (word.Rslts_done()) continue; // last db_search for word returned 0 results; don't search again;
|
||||
int offset = word.Rslts_offset();
|
||||
Xoa_app_.Usr_dlg().Prog_many("", "", "searching; wiki=~{0} total=~{1} offset=~{2} index=~{3} word=~{4}", wiki.Domain_str(), word_ary_len, offset, i, word.text);
|
||||
String sql = search_fmt.Bld_many_to_str_auto_bfr(link_tbl.Tbl_name(), link_tbl.Fld_page_id(), link_tbl.Fld_word_id(), word.id, offset); // need to return enough results to fill qry.page_len as many results may be discarded below; DATE:2015-04-24
|
||||
int rslts_found = Search_pages(cxl, rslt_lnr, cache, wiki, case_mgr, qry, page_tbl, attach_rdr, sql, ttl_matcher, word, rslts_wanted);
|
||||
total_found += rslts_found;
|
||||
if (rslts_found == -1) return; // canceled
|
||||
else if (rslts_found > 0) found_none = false; // NOTE: do not reverse and do rslts_found == 0; want to check if any word returns results;
|
||||
}
|
||||
if (found_none) {cache.Done_y_(); break;}
|
||||
if (total_found >= rslts_wanted) break;
|
||||
}
|
||||
cache.Itms_end_(qry.itms_end);
|
||||
cache.Sort();
|
||||
}
|
||||
catch (Exception e) {Gfo_usr_dlg_.Instance.Warn_many("", "", "error during search; wiki=~{0} total=~{1} err=~{2}", wiki.Domain_str(), word_ary_len, Err_.Message_gplx_log(e));}
|
||||
finally {attach_rdr.Detach();}
|
||||
}
|
||||
private int Search_pages(Cancelable cxl, Srch_rslt_lnr rslt_lnr, Srch_rslt_hash cache, Xow_wiki wiki, Xol_case_mgr case_mgr, Srch_qry qry
|
||||
, Xowd_page_tbl page_tbl, Db_attach_rdr attach_rdr, String sql, Srch_crt_node ttl_matcher, Srch_word_row word, int rslts_wanted) {
|
||||
int rslts_found = 0;
|
||||
Xow_ns_mgr ns_mgr = wiki.Ns_mgr();
|
||||
Db_rdr rdr = attach_rdr.Exec_as_rdr(sql);
|
||||
try {
|
||||
while (rdr.Move_next()) {
|
||||
if (cxl.Canceled()) return -1;
|
||||
word.Rslts_offset_add_1();
|
||||
int page_ns = rdr.Read_int(page_tbl.Fld_page_ns());
|
||||
if (!qry.ns_mgr.Has(page_ns)) continue; // ignore: ns doesn't match
|
||||
byte[] page_ttl = rdr.Read_bry_by_str(page_tbl.Fld_page_title());
|
||||
// Io_mgr.Instance.AppendFilStr("C:\\temp.txt", String_.new_u8(word.Text()) + "|" + Int_.To_str(page_ns) + "|" + String_.new_u8(page_ttl) + "\n");
|
||||
if (!ttl_matcher.Matches(case_mgr, page_ttl)) continue; // ignore: ttl doesn't match ttl_matcher
|
||||
Xow_ns ns = ns_mgr.Ids_get_or_null(page_ns);
|
||||
byte[] page_ttl_w_ns = ns.Gen_ttl(page_ttl);
|
||||
if (cache.Has(page_ttl_w_ns)) continue; // ignore: page already added by another word; EX: "A B"; word is "B", but "A B" already added by "A"
|
||||
Srch_rslt_itm row = new Srch_rslt_itm(wiki.Domain_bry(), wiki.Ttl_parse(page_ttl_w_ns), rdr.Read_int(page_tbl.Fld_page_id()), rdr.Read_int(page_tbl.Fld_page_len()));
|
||||
rslt_lnr.Notify_rslt_found(row);
|
||||
if (++rslts_found == rslts_wanted) break; // stop: found enough results; DATE:2015-04-24
|
||||
}
|
||||
} finally {rdr.Rls();}
|
||||
if (rslts_found == 0) word.Rslts_done_y_(); // read through entire rdr and nothing found; mark word done
|
||||
return rslts_found;
|
||||
}
|
||||
public Db_stmt New_qry(Db_conn conn, String page_db_alias, Xowd_page_tbl page, Xowd_search_link_tbl link, int offset) {
|
||||
Db_qry qry = Db_qry_.select_()
|
||||
.Cols_w_tbl_("p", page.Fld_page_id(), page.Fld_page_ns(), page.Fld_page_title(), page.Fld_page_len())
|
||||
.From_(page_db_alias, page.Tbl_name(), "p")
|
||||
.Join_(link.Tbl_name(), "l", Db_qry_.New_join__join(link.Fld_page_id(), page.Fld_page_id(), "p"))
|
||||
.Where_(Db_crt_.New_eq("l", link.Fld_word_id(), -1))
|
||||
.Order_("p", page.Fld_page_len(), Bool_.N)
|
||||
.Offset_(offset)
|
||||
;
|
||||
// qry_mgr.Add_ns(qry, page); // qry.Where_and_(page.Fld_page_ns(), -1)
|
||||
return conn.Stmt_new(qry);
|
||||
}
|
||||
private static final Bry_fmt search_fmt = Bry_fmt.New
|
||||
( String_.Concat_lines_nl_skip_last
|
||||
( "SELECT p.page_id"
|
||||
, ", p.page_namespace"
|
||||
, ", p.page_title"
|
||||
, ", p.page_len"
|
||||
, "FROM <attach_db>page p"
|
||||
, " JOIN ~{tbl_link} l ON p.page_id = l.~{col_link_page_id} "
|
||||
, "WHERE l.~{col_link_word_id} = ~{word_id}"
|
||||
, "ORDER BY p.page_len DESC"
|
||||
, "LIMIT -1" // NOTE:LIMIT needed when OFFSET is specified; -1 LIMIT means infinite; "If the LIMIT expression evaluates to a negative value, then there is no upper bound on the number of rows returned"; http://sqlite.org/lang_select.html
|
||||
, "OFFSET ~{offset};"
|
||||
), "tbl_link", "col_link_page_id", "col_link_word_id", "word_id", "offset");
|
||||
}
|
||||
44
400_xowa/src/gplx/xowa/specials/search/Srch_qry.java
Normal file
44
400_xowa/src/gplx/xowa/specials/search/Srch_qry.java
Normal file
@@ -0,0 +1,44 @@
|
||||
/*
|
||||
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.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.xowa.wikis.domains.*;
|
||||
class Srch_qry {
|
||||
private final List_adp cmd_list = List_adp_.new_();
|
||||
public Srch_qry(byte[] search_raw, int page_idx, int page_len, Xows_ns_mgr ns_mgr, boolean async_db, Xow_domain_itm[] wiki_domains) {
|
||||
this.search_raw = search_raw; this.page_idx = page_idx; this.page_len = page_len; this.ns_mgr = ns_mgr; this.async_db = async_db; this.wiki_domains = wiki_domains;
|
||||
this.itms_bgn = page_idx * page_len;
|
||||
this.itms_end = itms_bgn + page_len;
|
||||
this.page_max = page_idx; // default page_max to page_idx; adjust later when all results are known
|
||||
this.key = Bry_.Add_w_dlm(Byte_ascii.Pipe, search_raw, ns_mgr.To_hash_key());
|
||||
this.special_link_base_href = Bry_.Add(Bry_.new_a7("Special:Search/"), search_raw, Bry_.new_a7("?fulltext=y"));
|
||||
}
|
||||
public final byte[] key;
|
||||
public final byte[] search_raw;
|
||||
public final int page_idx;
|
||||
public final int page_len;
|
||||
public final int itms_bgn;
|
||||
public final int itms_end;
|
||||
public final Xows_ns_mgr ns_mgr;
|
||||
public final Xow_domain_itm[] wiki_domains;
|
||||
public final byte[] special_link_base_href;
|
||||
public final boolean async_db;
|
||||
public int page_max;
|
||||
public int Cmds__len() {return cmd_list.Count();}
|
||||
public Xows_ui_cmd Cmds__get_at(int i) {return (Xows_ui_cmd)cmd_list.Get_at(i);}
|
||||
public void Cmds__add(Xows_ui_cmd cmd) {cmd_list.Add(cmd);}
|
||||
}
|
||||
@@ -16,27 +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.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.xowa.specials.search.parsers_old.*;
|
||||
class Xows_db_cache { // one cache per search term; EX: "Earth* AND (History OR Future) AND -"middle earth"" is one cache
|
||||
import gplx.xowa.specials.search.crts.*;
|
||||
class Srch_rslt_hash { // per search request; EX: 'Earth* AND (History OR Future) AND -"middle earth"'
|
||||
private final Ordered_hash hash = Ordered_hash_.New_bry();
|
||||
public Xows_db_word[] Words() {return words;} private Xows_db_word[] words; // words in cache; EX: earth, history, future but not "middle earth" (since not'ed)
|
||||
public Xows_db_matcher Matcher() {return matcher;} private Xows_db_matcher matcher; // criteria
|
||||
public boolean Done() {return done;} public void Done_y_() {done = true;} private boolean done; // marks if db search is done
|
||||
public Srch_crt_node Ttl_matcher() {return ttl_matcher;} private Srch_crt_node ttl_matcher;
|
||||
public Srch_word_row[] Words() {return words;} private Srch_word_row[] words; // words to search db; EX: earth, history, future but not "middle earth" (since not'ed)
|
||||
public boolean Done() {return done;} public void Done_y_() {done = true;} private boolean done; // marks if db search is done
|
||||
public int Count() {return hash.Count();}
|
||||
public int Itms_end() {return itms_end;} public void Itms_end_(int v) {itms_end = v;} private int itms_end;
|
||||
public void Init_by_db(Cancelable cxl, byte[] raw, gplx.xowa.wikis.data.tbls.Xowd_search_word_tbl word_tbl) {
|
||||
this.matcher = new Xow_search_parser().Parse(raw);
|
||||
this.words = new Xows_db_matcher_bldr().Gather_words_for_db(cxl, matcher, word_tbl);
|
||||
this.ttl_matcher = new Srch_crt_parser().Parse(raw);
|
||||
this.words = new Xows_db_matcher_bldr().Gather_words_for_db(cxl, ttl_matcher, word_tbl);
|
||||
}
|
||||
public boolean Has(byte[] key) {return hash.Has(key);}
|
||||
public Xows_db_row Get_at(int i) {return (Xows_db_row)hash.Get_at(i);}
|
||||
public void Add(Xows_db_row row) {hash.Add(row.Page_ttl().Full_db(), row);}
|
||||
public void Get_between(Xows_ui_rslt search_ui, int bgn, int end) {
|
||||
public boolean Has(byte[] key) {return hash.Has(key);}
|
||||
public Srch_rslt_itm Get_at(int i) {return (Srch_rslt_itm)hash.Get_at(i);}
|
||||
public void Add(Srch_rslt_itm itm) {hash.Add(itm.page_ttl.Full_db(), itm);}
|
||||
public void Get_between(Srch_rslt_list search_ui, int bgn, int end) {
|
||||
if (bgn >= hash.Count()) return; // requested start not in cache; exit
|
||||
for (int i = bgn; i < end; ++i) {
|
||||
if (i >= hash.Count()) break;
|
||||
search_ui.Add((Xows_db_row)hash.Get_at(i));
|
||||
search_ui.Add((Srch_rslt_itm)hash.Get_at(i));
|
||||
}
|
||||
}
|
||||
public void Sort() {hash.Sort_by(Xows_db_row_sorter.Page_len_dsc);}
|
||||
public void Sort() {hash.Sort_by(Srch_rslt_itm_sorter.Page_len_dsc);}
|
||||
}
|
||||
40
400_xowa/src/gplx/xowa/specials/search/Srch_rslt_itm.java
Normal file
40
400_xowa/src/gplx/xowa/specials/search/Srch_rslt_itm.java
Normal file
@@ -0,0 +1,40 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
public class Srch_rslt_itm {
|
||||
public final byte[] key;
|
||||
public final byte[] wiki_bry;
|
||||
public final Xoa_ttl page_ttl;
|
||||
public final int page_id;
|
||||
public final int page_len;
|
||||
public Srch_rslt_itm(byte[] wiki_bry, Xoa_ttl page_ttl, int page_id, int page_len) {
|
||||
this.wiki_bry = wiki_bry;
|
||||
this.page_ttl = page_ttl;
|
||||
this.page_id = page_id;
|
||||
this.page_len = page_len;
|
||||
this.key = Bry_.Add(wiki_bry, Byte_ascii.Pipe_bry, page_ttl.Full_db());
|
||||
}
|
||||
}
|
||||
class Srch_rslt_itm_sorter implements gplx.core.lists.ComparerAble {
|
||||
public int compare(Object lhsObj, Object rhsObj) {
|
||||
Srch_rslt_itm lhs = (Srch_rslt_itm)lhsObj;
|
||||
Srch_rslt_itm rhs = (Srch_rslt_itm)rhsObj;
|
||||
return -Int_.Compare(lhs.page_len, rhs.page_len);
|
||||
}
|
||||
public static final Srch_rslt_itm_sorter Page_len_dsc = new Srch_rslt_itm_sorter(); Srch_rslt_itm_sorter() {}
|
||||
}
|
||||
@@ -16,9 +16,9 @@ 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.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
class Xows_ui_rslt {
|
||||
private final List_adp rslt_list = List_adp_.new_();
|
||||
public int Len() {return rslt_list.Count();}
|
||||
public void Add(Xows_db_row rslt) {rslt_list.Add(rslt);}
|
||||
public Xows_db_row Get_at(int i) {return (Xows_db_row)rslt_list.Get_at(i);}
|
||||
class Srch_rslt_list {
|
||||
private final List_adp list = List_adp_.new_();
|
||||
public int Len() {return list.Count();}
|
||||
public void Add(Srch_rslt_itm rslt) {list.Add(rslt);}
|
||||
public Srch_rslt_itm Get_at(int i) {return (Srch_rslt_itm)list.Get_at(i);}
|
||||
}
|
||||
@@ -16,6 +16,6 @@ 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.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
public interface Xows_ui_async {
|
||||
void Add(Xows_db_row new_row);
|
||||
public interface Srch_rslt_lnr {
|
||||
void Notify_rslt_found(Srch_rslt_itm rslt);
|
||||
}
|
||||
@@ -16,21 +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.xowa.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
public class Xows_db_word {
|
||||
public Xows_db_word(int id, byte[] text, int page_count) {this.id = id; this.text = text; this.page_count = page_count;}
|
||||
public int Id() {return id;} private final int id;
|
||||
public byte[] Text() {return text;} private final byte[] text;
|
||||
public int Page_count() {return page_count;} private final int page_count;
|
||||
public class Srch_word_row {
|
||||
public Srch_word_row(int id, byte[] text, int page_count) {this.id = id; this.text = text; this.page_count = page_count;}
|
||||
public final int id;
|
||||
public final byte[] text;
|
||||
public final int page_count;
|
||||
public int Rslts_offset() {return rslts_offset;} private int rslts_offset;
|
||||
public boolean Rslts_done() {return rslts_done;} private boolean rslts_done;
|
||||
public void Rslts_offset_add_1() {++rslts_offset;}
|
||||
public void Rslts_done_y_() {rslts_done = true;}
|
||||
}
|
||||
class Xows_db_word_sorter implements gplx.core.lists.ComparerAble {
|
||||
class Srch_word_row_sorter implements gplx.core.lists.ComparerAble {
|
||||
public int compare(Object lhsObj, Object rhsObj) {
|
||||
Xows_db_word lhs = (Xows_db_word)lhsObj;
|
||||
Xows_db_word rhs = (Xows_db_word)rhsObj;
|
||||
return -Int_.Compare(lhs.Page_count(), rhs.Page_count());
|
||||
Srch_word_row lhs = (Srch_word_row)lhsObj;
|
||||
Srch_word_row rhs = (Srch_word_row)rhsObj;
|
||||
return -Int_.Compare(lhs.page_count, rhs.page_count);
|
||||
}
|
||||
public static final Xows_db_word_sorter Page_count_dsc = new Xows_db_word_sorter(); Xows_db_word_sorter() {}
|
||||
public static final Srch_word_row_sorter Page_count_dsc = new Srch_word_row_sorter(); Srch_word_row_sorter() {}
|
||||
}
|
||||
@@ -24,17 +24,17 @@ class Xows_core {
|
||||
private boolean ask_for_upgrade = true; private final Hash_adp_bry upgraded_wikis = Hash_adp_bry.cs();
|
||||
public Xows_core(Xoae_wiki_mgr wiki_mgr) {this.wiki_mgr = wiki_mgr;}
|
||||
private final Xows_html_wkr html_wkr = new Xows_html_wkr();
|
||||
public Xows_db_cache Get_cache_or_new(byte[] key) {
|
||||
Xows_db_cache cache = (Xows_db_cache)cache_hash.Get_by_bry(key);
|
||||
public Srch_rslt_hash Get_cache_or_new(byte[] key) {
|
||||
Srch_rslt_hash cache = (Srch_rslt_hash)cache_hash.Get_by_bry(key);
|
||||
if (cache == null) {
|
||||
cache = new Xows_db_cache();
|
||||
cache = new Srch_rslt_hash();
|
||||
cache_hash.Add_bry_obj(key, cache);
|
||||
}
|
||||
return cache;
|
||||
}
|
||||
public void Search(Xow_wiki search_wiki, Xoae_page page, Xows_ui_qry qry) {
|
||||
public void Search(Xow_wiki search_wiki, Xoae_page page, Srch_qry qry) {
|
||||
// generate 1 cmd per wiki
|
||||
Xow_domain_itm[] domain_ary = qry.Wiki_domains(); int domain_ary_len = domain_ary.length;
|
||||
Xow_domain_itm[] domain_ary = qry.wiki_domains; int domain_ary_len = domain_ary.length;
|
||||
for (int i = 0; i < domain_ary_len; ++i) {
|
||||
Xow_domain_itm domain = domain_ary[i];
|
||||
try {
|
||||
@@ -44,7 +44,7 @@ class Xows_core {
|
||||
qry.Cmds__add(cmd);
|
||||
} catch (Exception e) {Xoa_app_.Usr_dlg().Warn_many("", "", "search:wiki failed; wiki=~{0} err=~{1}", domain.Domain_str(), Err_.Message_lang(e));} // handle bad wikis, like "en.wikipedia.org-old"; DATE:2015-04-24
|
||||
}
|
||||
qry.Page_max_(Int_.Max_value);
|
||||
qry.page_max = Int_.Max_value;
|
||||
// do search and generate html
|
||||
html_wkr.Init_by_wiki(search_wiki, search_wiki.Lang().Num_mgr(), qry);
|
||||
int cmds_len = qry.Cmds__len();
|
||||
|
||||
@@ -1,68 +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.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.langs.regxs.*;
|
||||
public class Xows_db_matcher {
|
||||
private final Gfo_pattern raw_pattern;
|
||||
public Xows_db_matcher(int tid, byte[] raw, Xows_db_matcher lhs, Xows_db_matcher rhs) {
|
||||
this.tid = tid; this.raw = raw; this.lhs = lhs; this.rhs = rhs;
|
||||
this.raw_pattern = Bry_.Has(raw, Byte_ascii.Star) ? new Gfo_pattern(raw) : null;
|
||||
}
|
||||
public int Tid() {return tid;} private final int tid;
|
||||
public int Page_count() {return page_count;} public void Page_count_(int v) {page_count = v;} private int page_count;
|
||||
public byte[] Raw() {return raw;} private final byte[] raw;
|
||||
public Xows_db_matcher Lhs() {return lhs;} private final Xows_db_matcher lhs;
|
||||
public Xows_db_matcher Rhs() {return rhs;} private final Xows_db_matcher rhs;
|
||||
public boolean Matches(byte[] page_ttl_lc, byte[][] page_ttl_words) {
|
||||
switch (tid) {
|
||||
case Xows_db_matcher.Tid_word: {
|
||||
int len = page_ttl_words.length;
|
||||
for (int i = 0; i < len; ++i) {
|
||||
byte[] word = page_ttl_words[i];
|
||||
if (raw_pattern == null) {
|
||||
if (Bry_.Eq(word, raw)) return true;
|
||||
}
|
||||
else {
|
||||
if (raw_pattern.Match(word)) return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
case Xows_db_matcher.Tid_word_quote: // note that raw does not have quotes; EX: "B*" -> B*
|
||||
return Bry_find_.Find_fwd(page_ttl_lc, raw) != Bry_find_.Not_found;
|
||||
case Xows_db_matcher.Tid_not:
|
||||
return !rhs.Matches(page_ttl_lc, page_ttl_words);
|
||||
case Xows_db_matcher.Tid_or:
|
||||
return lhs.Matches(page_ttl_lc, page_ttl_words) || rhs.Matches(page_ttl_lc, page_ttl_words);
|
||||
case Xows_db_matcher.Tid_and:
|
||||
return lhs.Matches(page_ttl_lc, page_ttl_words) && rhs.Matches(page_ttl_lc, page_ttl_words);
|
||||
case Xows_db_matcher.Tid_null: return false;
|
||||
default: throw Err_.new_unhandled(tid);
|
||||
}
|
||||
}
|
||||
public static final Xows_db_matcher Null = new Xows_db_matcher(Xows_db_matcher.Tid_null, null, null, null);
|
||||
public static Xows_db_matcher new_join(byte tid, Xows_db_matcher lhs, Xows_db_matcher rhs) {return new Xows_db_matcher(tid, null, lhs, rhs);}
|
||||
public static final int
|
||||
Tid_word = 0
|
||||
, Tid_and = 1
|
||||
, Tid_or = 2
|
||||
, Tid_not = 3
|
||||
, Tid_word_quote = 4
|
||||
, Tid_null = 5
|
||||
;
|
||||
}
|
||||
@@ -17,47 +17,48 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.xowa.wikis.data.tbls.*;
|
||||
import gplx.xowa.specials.search.crts.*;
|
||||
class Xows_db_matcher_bldr {
|
||||
public Xows_db_word[] Gather_words_for_db(Cancelable cxl, Xows_db_matcher matcher, Xowd_search_word_tbl word_tbl) {
|
||||
public Srch_word_row[] Gather_words_for_db(Cancelable cxl, Srch_crt_node matcher, Xowd_search_word_tbl word_tbl) {
|
||||
List_adp rv = List_adp_.new_();
|
||||
Gather_words_for_db(cxl, matcher, rv, word_tbl);
|
||||
rv.Sort_by(Xows_db_word_sorter.Page_count_dsc);
|
||||
return (Xows_db_word[])rv.To_ary(Xows_db_word.class);
|
||||
rv.Sort_by(Srch_word_row_sorter.Page_count_dsc);
|
||||
return (Srch_word_row[])rv.To_ary(Srch_word_row.class);
|
||||
}
|
||||
private void Gather_words_for_db(Cancelable cxl, Xows_db_matcher matcher, List_adp rv, Xowd_search_word_tbl word_tbl) {
|
||||
switch (matcher.Tid()) {
|
||||
case Xows_db_matcher.Tid_word:
|
||||
byte[] word_text = matcher.Raw();
|
||||
private void Gather_words_for_db(Cancelable cxl, Srch_crt_node matcher, List_adp rv, Xowd_search_word_tbl word_tbl) {
|
||||
switch (matcher.tid) {
|
||||
case Srch_crt_node.Tid_word:
|
||||
byte[] word_text = matcher.raw;
|
||||
if (Bry_.Has(word_text, Byte_ascii.Star))
|
||||
Load_word_many(cxl, rv, word_text, word_tbl);
|
||||
else
|
||||
Load_word_one(rv, word_text, word_tbl);
|
||||
break;
|
||||
case Xows_db_matcher.Tid_word_quote:
|
||||
case Srch_crt_node.Tid_word_quote:
|
||||
List_adp tmp = List_adp_.new_();
|
||||
byte[][] words = Bry_split_.Split(matcher.Raw(), Byte_ascii.Space, Bool_.Y);
|
||||
byte[][] words = Bry_split_.Split(matcher.raw, Byte_ascii.Space, Bool_.Y);
|
||||
int words_len = words.length;
|
||||
for (int i = 0; i < words_len; ++i) {
|
||||
byte[] word = words[i];
|
||||
Load_word_one(tmp, word, word_tbl);
|
||||
}
|
||||
if (tmp.Count() == 0) return; // no words in db; EX: "xyz cba"
|
||||
tmp.Sort_by(Xows_db_word_sorter.Page_count_dsc);
|
||||
tmp.Sort_by(Srch_word_row_sorter.Page_count_dsc);
|
||||
rv.Add(tmp.Get_at(0)); // add lowest page_count word to db; EX: search for "earth and" should search for "earth" only, but match for "earth and"
|
||||
break;
|
||||
case Xows_db_matcher.Tid_and:
|
||||
case Srch_crt_node.Tid_and:
|
||||
List_adp lhs_tmp = List_adp_.new_(), rhs_tmp = List_adp_.new_();
|
||||
Gather_words_for_db(cxl, matcher.Lhs(), lhs_tmp, word_tbl);
|
||||
Gather_words_for_db(cxl, matcher.Rhs(), rhs_tmp, word_tbl);
|
||||
Gather_words_for_db(cxl, matcher.lhs, lhs_tmp, word_tbl);
|
||||
Gather_words_for_db(cxl, matcher.rhs, rhs_tmp, word_tbl);
|
||||
List_adp_.Add_list(rv, Calc_lowest(lhs_tmp, rhs_tmp)); // calc side with lowest count; add to rv;
|
||||
break;
|
||||
case Xows_db_matcher.Tid_or:
|
||||
Gather_words_for_db(cxl, matcher.Lhs(), rv, word_tbl);
|
||||
Gather_words_for_db(cxl, matcher.Rhs(), rv, word_tbl);
|
||||
case Srch_crt_node.Tid_or:
|
||||
Gather_words_for_db(cxl, matcher.lhs, rv, word_tbl);
|
||||
Gather_words_for_db(cxl, matcher.rhs, rv, word_tbl);
|
||||
break;
|
||||
case Xows_db_matcher.Tid_not: break; // never add "NOT" to db_search
|
||||
case Xows_db_matcher.Tid_null: break; // should not happen
|
||||
default: throw Err_.new_unhandled(matcher.Tid());
|
||||
case Srch_crt_node.Tid_not: break; // never add "NOT" to db_search
|
||||
case Srch_crt_node.Tid_null: break; // should not happen
|
||||
default: throw Err_.new_unhandled(matcher.tid);
|
||||
}
|
||||
}
|
||||
private List_adp Calc_lowest(List_adp lhs, List_adp rhs) {
|
||||
@@ -72,15 +73,15 @@ class Xows_db_matcher_bldr {
|
||||
int rv = 0;
|
||||
int len = list.Count();
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Xows_db_word word = (Xows_db_word)list.Get_at(i);
|
||||
rv += word.Page_count();
|
||||
Srch_word_row word = (Srch_word_row)list.Get_at(i);
|
||||
rv += word.page_count;
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
private void Load_word_one(List_adp rv, byte[] word_text, Xowd_search_word_tbl word_tbl) {
|
||||
Xoa_app_.Usr_dlg().Prog_many("", "", "search:word by text; word=~{0}", word_text);
|
||||
Xowd_search_word_row row = word_tbl.Select_by_or_null(word_text); if (row == Xowd_search_word_row.Null) return;
|
||||
Xows_db_word word = new Xows_db_word(row.Id(), row.Text(), row.Page_count());
|
||||
Srch_word_row word = new Srch_word_row(row.Id(), row.Text(), row.Page_count());
|
||||
rv.Add(word);
|
||||
}
|
||||
private void Load_word_many(Cancelable cxl, List_adp rv, byte[] word_text, Xowd_search_word_tbl word_tbl) {
|
||||
@@ -89,7 +90,7 @@ class Xows_db_matcher_bldr {
|
||||
int len = rows.length;
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Xowd_search_word_row row = rows[i];
|
||||
rv.Add(new Xows_db_word(row.Id(), row.Text(), row.Page_count()));
|
||||
rv.Add(new Srch_word_row(row.Id(), row.Text(), row.Page_count()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,41 +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.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
public class Xows_db_row {
|
||||
public Xows_db_row(byte[] wiki_domain, Xoa_ttl page_ttl, int page_id, int page_len) {
|
||||
this.wiki_domain = wiki_domain;
|
||||
this.page_ttl = page_ttl;
|
||||
this.page_id = page_id;
|
||||
this.page_len = page_len;
|
||||
this.key = Bry_.Add(wiki_domain, Byte_ascii.Pipe_bry, page_ttl.Full_db());
|
||||
}
|
||||
public byte[] Key() {return key;} private final byte[] key;
|
||||
public byte[] Wiki_domain() {return wiki_domain;} private final byte[] wiki_domain;
|
||||
public Xoa_ttl Page_ttl() {return page_ttl;} private final Xoa_ttl page_ttl;
|
||||
public int Page_id() {return page_id;} private final int page_id;
|
||||
public int Page_len() {return page_len;} private final int page_len;
|
||||
public static Xows_db_row[] Ary(Xows_db_row... v) {return v;}
|
||||
}
|
||||
class Xows_db_row_sorter implements gplx.core.lists.ComparerAble {
|
||||
public int compare(Object lhsObj, Object rhsObj) {
|
||||
Xows_db_row lhs = (Xows_db_row)lhsObj;
|
||||
Xows_db_row rhs = (Xows_db_row)rhsObj;
|
||||
return -Int_.Compare(lhs.Page_len(), rhs.Page_len());
|
||||
}
|
||||
public static final Xows_db_row_sorter Page_len_dsc = new Xows_db_row_sorter(); Xows_db_row_sorter() {}
|
||||
}
|
||||
@@ -1,125 +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.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.core.primitives.*; import gplx.dbs.*;
|
||||
import gplx.xowa.wikis.nss.*;
|
||||
import gplx.xowa.wikis.data.*; import gplx.xowa.wikis.data.tbls.*; import gplx.xowa.langs.cases.*;
|
||||
import gplx.gfui.*;
|
||||
public class Xows_db_wkr {
|
||||
private Xol_case_mgr drd_case_mgr;
|
||||
public Xows_db_row[] Search_by_drd(Cancelable cancelable, Xow_wiki wiki, Xows_ui_async ui_async, byte[] search, int search_results_max) {
|
||||
Xows_ns_mgr ns_mgr = new Xows_ns_mgr(); ns_mgr.Add_main_if_empty();
|
||||
Xows_ui_qry qry = new Xows_ui_qry(search, 0, search_results_max, Xosrh_rslt_itm_sorter.Tid_len_dsc, ns_mgr, Bool_.Y, new gplx.xowa.wikis.domains.Xow_domain_itm[] {wiki.Domain_itm()});
|
||||
Xows_ui_rslt rslt = new Xows_ui_rslt();
|
||||
Xows_db_cache cache = new Xows_db_cache(); cache.Init_by_db(Cancelable_.Never, search, wiki.Data__core_mgr().Db__search().Tbl__search_word());
|
||||
Xows_ui_cmd cmd = new Xows_ui_cmd(null, qry, wiki, null, null, null, cache, ui_async);
|
||||
if (drd_case_mgr == null) drd_case_mgr = Xol_case_mgr_.U8();
|
||||
Search(cancelable, cmd, qry, rslt, cache, wiki, drd_case_mgr);
|
||||
int len = cache.Count();
|
||||
Xows_db_row[] rv = new Xows_db_row[len];
|
||||
for (int i = 0; i < len; ++i)
|
||||
rv[i] = cache.Get_at(i);
|
||||
return rv;
|
||||
}
|
||||
@gplx.Internal protected void Search(Cancelable cancelable, Xows_ui_cmd cmd, Xows_ui_qry qry, Xows_ui_rslt rslt, Xows_db_cache cache, Xow_wiki wiki, Xol_case_mgr case_mgr) {
|
||||
// assert matcher
|
||||
Xowd_db_file search_db = wiki.Data__core_mgr().Db__search();
|
||||
Xoa_app_.Usr_dlg().Prog_many("", "", "search started (please wait)");
|
||||
Xows_db_matcher matcher = cache.Matcher();
|
||||
if (matcher == null) {
|
||||
cache.Init_by_db
|
||||
( cmd
|
||||
, wiki.Lang().Case_mgr().Case_build_lower(qry.Search_raw()) // lower-case search
|
||||
, search_db.Tbl__search_word()
|
||||
);
|
||||
matcher = cache.Matcher();
|
||||
}
|
||||
// init
|
||||
int rslts_wanted = qry.Itms_end() - qry.Itms_bgn();
|
||||
Xowd_db_file core_db = wiki.Data__core_mgr().Db__core();
|
||||
Xowd_page_tbl page_tbl = core_db.Tbl__page();
|
||||
Xowd_search_link_tbl link_tbl = search_db.Tbl__search_link();
|
||||
Xows_db_word[] word_ary = cache.Words(); int word_ary_len = word_ary.length;
|
||||
// read pages for each word from db
|
||||
Db_attach_rdr attach_rdr = new Db_attach_rdr(search_db.Conn(), "page_db", core_db.Url());
|
||||
attach_rdr.Attach();
|
||||
int total_found = 0;
|
||||
try {
|
||||
while (true) {
|
||||
boolean found_none = true;
|
||||
for (int i = 0; i < word_ary_len; ++i) { // loop each word to get rslts_wanted
|
||||
if (cancelable.Canceled()) return;
|
||||
Xows_db_word word = word_ary[i];
|
||||
if (word.Rslts_done()) continue; // last db_search for word returned 0 results; don't search again;
|
||||
int offset = word.Rslts_offset();
|
||||
Xoa_app_.Usr_dlg().Prog_many("", "", "searching; wiki=~{0} total=~{1} offset=~{2} index=~{3} word=~{4}", wiki.Domain_str(), word_ary_len, offset, i, word.Text());
|
||||
String sql = String_.Format(Search_sql, link_tbl.Tbl_name(), link_tbl.Fld_page_id(), link_tbl.Fld_word_id(), word.Id(), "page_len", "DESC", Int_.Max_value, offset); // need to return enough results to fill qry.Page_len() as many results may be discarded below; DATE:2015-04-24
|
||||
int rslts_found = Search_pages(cancelable, cmd, qry, rslt, cache, wiki, case_mgr, page_tbl, attach_rdr, sql, word, matcher, rslts_wanted);
|
||||
total_found += rslts_found;
|
||||
if (rslts_found == -1) return; // canceled
|
||||
else if (rslts_found > 0) found_none = false; // NOTE: do not reverse and do rslts_found == 0; want to check if any word returns results;
|
||||
}
|
||||
if (found_none) {cache.Done_y_(); break;}
|
||||
if (total_found >= rslts_wanted) break;
|
||||
}
|
||||
cache.Itms_end_(qry.Itms_end());
|
||||
cache.Sort();
|
||||
} finally {attach_rdr.Detach();}
|
||||
}
|
||||
private int Search_pages(Cancelable cancelable, Xows_ui_cmd cmd, Xows_ui_qry qry, Xows_ui_rslt rslt, Xows_db_cache cache, Xow_wiki wiki, Xol_case_mgr case_mgr, Xowd_page_tbl page_tbl, Db_attach_rdr attach_rdr, String sql, Xows_db_word word, Xows_db_matcher matcher, int rslts_wanted) {
|
||||
int rslts_found = 0;
|
||||
Xow_ns_mgr ns_mgr = wiki.Ns_mgr();
|
||||
Db_rdr rdr = attach_rdr.Exec_as_rdr(sql);
|
||||
try {
|
||||
while (rdr.Move_next()) {
|
||||
if (cancelable.Canceled()) return -1;
|
||||
word.Rslts_offset_add_1();
|
||||
int page_ns = rdr.Read_int(page_tbl.Fld_page_ns());
|
||||
if (!qry.Ns_mgr().Has(page_ns)) continue; // ignore: ns doesn't match
|
||||
byte[] page_ttl = rdr.Read_bry_by_str(page_tbl.Fld_page_title());
|
||||
// Io_mgr.Instance.AppendFilStr("C:\\temp.txt", String_.new_u8(word.Text()) + "|" + Int_.To_str(page_ns) + "|" + String_.new_u8(page_ttl) + "\n");
|
||||
byte[] page_ttl_lc = case_mgr.Case_build_lower(Xoa_ttl.Replace_unders(page_ttl));
|
||||
byte[][] page_ttl_words = Bry_split_.Split(page_ttl_lc, Byte_ascii.Space, Bool_.Y);
|
||||
if (!matcher.Matches(page_ttl_lc, page_ttl_words)) continue; // ignore: ttl doesn't match matcher
|
||||
int page_id = rdr.Read_int(page_tbl.Fld_page_id());
|
||||
int page_len = rdr.Read_int(page_tbl.Fld_page_len());
|
||||
Xow_ns ns = ns_mgr.Ids_get_or_null(page_ns);
|
||||
byte[] page_ttl_w_ns = ns.Gen_ttl(page_ttl);
|
||||
if (cache.Has(page_ttl_w_ns)) continue; // ignore: page already added by another word; EX: "A B"; word is "B", but "A B" already added by "A"
|
||||
Xoa_ttl ttl = wiki.Ttl_parse(page_ttl_w_ns);
|
||||
Xows_db_row row = new Xows_db_row(wiki.Domain_bry(), ttl, page_id, page_len);
|
||||
cmd.Add_rslt(row);
|
||||
if (++rslts_found == rslts_wanted) break; // stop: found enough results; DATE:2015-04-24
|
||||
}
|
||||
} finally {rdr.Rls();}
|
||||
if (rslts_found == 0) word.Rslts_done_y_(); // read through entire rdr and nothing found; mark word done
|
||||
return rslts_found;
|
||||
}
|
||||
private static final String Search_sql = String_.Concat_lines_nl_skip_last
|
||||
( "SELECT cp.page_id"
|
||||
, ", cp.page_namespace"
|
||||
, ", cp.page_title"
|
||||
, ", cp.page_len"
|
||||
, "FROM {0} sp"
|
||||
, " JOIN <attach_db>page cp ON cp.page_id = sp.{1} "
|
||||
, "WHERE sp.{2} = {3}"
|
||||
, "ORDER BY {4} {5}"
|
||||
, "LIMIT {6}"
|
||||
, "OFFSET {7};"
|
||||
);
|
||||
}
|
||||
@@ -20,34 +20,34 @@ import gplx.core.brys.fmtrs.*;
|
||||
import gplx.langs.htmls.*; import gplx.xowa.htmls.core.htmls.utls.*; import gplx.xowa.langs.numbers.*;
|
||||
class Xows_html_wkr {
|
||||
private final Bry_bfr tmp_bfr = Bry_bfr.new_(255);
|
||||
private Xows_ui_qry qry; private Xow_wiki wiki; private Xol_num_mgr num_mgr;
|
||||
private Srch_qry qry; private Xow_wiki wiki; private Xol_num_mgr num_mgr;
|
||||
private Xoh_lnki_bldr lnki_bldr; private Xoh_anchor_kv_bldr self_lnkr = new Xoh_anchor_kv_bldr(); private Xows_html_row html_rows;
|
||||
public void Init_by_wiki(Xow_wiki wiki, Xol_num_mgr num_mgr, Xows_ui_qry qry) {
|
||||
public void Init_by_wiki(Xow_wiki wiki, Xol_num_mgr num_mgr, Srch_qry qry) {
|
||||
this.wiki = wiki; this.num_mgr = num_mgr; this.qry = qry;
|
||||
this.lnki_bldr = wiki.App().Html__lnki_bldr();
|
||||
this.html_rows = new Xows_html_row(lnki_bldr);
|
||||
self_lnkr.Init_w_qarg(qry.Special_link_base_href());
|
||||
self_lnkr.Init_w_qarg(qry.special_link_base_href);
|
||||
}
|
||||
public byte[] Gen_page(byte[] tbls) {
|
||||
byte[] rslts_hdr = fmtr_rslts.Bld_bry_many(tmp_bfr, num_mgr.Format_num(qry.Itms_bgn() + List_adp_.Base1), num_mgr.Format_num(qry.Itms_end()), qry.Search_raw());
|
||||
byte[] rslts_hdr = fmtr_rslts.Bld_bry_many(tmp_bfr, num_mgr.Format_num(qry.itms_bgn + List_adp_.Base1), num_mgr.Format_num(qry.itms_end), qry.search_raw);
|
||||
byte[] option_link = lnki_bldr.Href_(Bry_.new_a7("home"), wiki.Ttl_parse(Bry_.new_a7("Help:Options/Search"))).Img_16x16(Xoh_img_path.Img_option).Bld_to_bry();
|
||||
fmtr_page.Bld_bfr_many(tmp_bfr, rslts_hdr, option_link, Paging_link(Bool_.N), Paging_link(Bool_.Y), tbls);
|
||||
return tmp_bfr.To_bry_and_clear();
|
||||
}
|
||||
public void Gen_tbl(Bry_bfr bfr, Xows_ui_rslt rslt, byte[] cmd_key, byte[] wiki_domain, boolean searching_db) {
|
||||
public void Gen_tbl(Bry_bfr bfr, Srch_rslt_list rslt, byte[] cmd_key, byte[] wiki_domain, boolean searching_db) {
|
||||
html_rows.Init(rslt);
|
||||
byte[] search_link = lnki_bldr.Href_(wiki_domain, wiki.Ttl_parse(self_lnkr.Bld_to_bry())).Caption_(wiki_domain).Img_16x16(Xoh_img_path.Img_search).Img_pos_is_left_(Bool_.Y).Bld_to_bry();
|
||||
fmtr_tbl.Bld_bfr_many(bfr, search_link, searching_db ? Cancel_link(wiki_domain, cmd_key) : Bry_.Empty, Bry_hdr_len, Bry_hdr_ttl, Xows_ui_async__html.Gen_insert_key(wiki_domain), html_rows);
|
||||
}
|
||||
private byte[] Cancel_link(byte[] domain, byte[] cmd_key) {
|
||||
lnki_bldr.Id_(Bry_.Add(Bry_.new_a7("xowa_cancel_"), domain));
|
||||
lnki_bldr.Href_(wiki, self_lnkr.Add_int(Xows_arg_mgr.Arg_bry_page_index, qry.Page_idx()).Add_bry(Xows_arg_mgr.Arg_bry_cancel, cmd_key).Bld_to_bry());
|
||||
lnki_bldr.Href_(wiki, self_lnkr.Add_int(Xows_arg_mgr.Arg_bry_page_index, qry.page_idx).Add_bry(Xows_arg_mgr.Arg_bry_cancel, cmd_key).Bld_to_bry());
|
||||
lnki_bldr.Title_(Bry_cancel);
|
||||
lnki_bldr.Img_16x16(Xoh_img_path.Img_cancel);
|
||||
return lnki_bldr.Bld_to_bry();
|
||||
}
|
||||
public byte[] Paging_link(boolean fwd) {
|
||||
int paging_idx = qry.Page_idx();
|
||||
int paging_idx = qry.page_idx;
|
||||
byte[] title = null, img_path = Bry_.Empty;
|
||||
boolean img_pos_is_left = true;
|
||||
if (fwd) {
|
||||
@@ -92,24 +92,24 @@ class Xows_html_wkr {
|
||||
;
|
||||
}
|
||||
class Xows_html_row implements gplx.core.brys.Bfr_arg {
|
||||
private final Xoh_lnki_bldr lnki_bldr; private Xows_ui_rslt rslt;
|
||||
private final Xoh_lnki_bldr lnki_bldr; private Srch_rslt_list rslt;
|
||||
private final Object thread_lock = new Object();
|
||||
public Xows_html_row(Xoh_lnki_bldr lnki_bldr) {this.lnki_bldr = lnki_bldr;}
|
||||
public Xows_html_row Init(Xows_ui_rslt rslt) {this.rslt = rslt; return this;}
|
||||
public Xows_html_row Init(Srch_rslt_list rslt) {this.rslt = rslt; return this;}
|
||||
public void Bfr_arg__add(Bry_bfr bfr) { // <a href="/wiki/A" title="A" class="xowa-visited">A</a>
|
||||
int len = rslt.Len();
|
||||
for (int i = 0; i < len; ++i) {
|
||||
Xows_db_row row = rslt.Get_at(i);
|
||||
Srch_rslt_itm row = rslt.Get_at(i);
|
||||
Gen_html(bfr, row);
|
||||
}
|
||||
}
|
||||
public void Gen_html(Bry_bfr bfr, Xows_db_row row) {
|
||||
public void Gen_html(Bry_bfr bfr, Srch_rslt_itm row) {
|
||||
synchronized (thread_lock) {
|
||||
lnki_bldr.Href_(row.Wiki_domain(), row.Page_ttl());
|
||||
byte[] title = row.Page_ttl().Full_txt();
|
||||
lnki_bldr.Href_(row.wiki_bry, row.page_ttl);
|
||||
byte[] title = row.page_ttl.Full_txt();
|
||||
lnki_bldr.Title_(title);
|
||||
lnki_bldr.Caption_(title);
|
||||
fmtr.Bld_bfr_many(bfr, Gfh_utl.Encode_id_as_str(row.Key()), row.Page_len(), lnki_bldr.Bld_to_bry());
|
||||
fmtr.Bld_bfr_many(bfr, Gfh_utl.Encode_id_as_str(row.key), row.page_len, lnki_bldr.Bld_to_bry());
|
||||
}
|
||||
}
|
||||
public Bry_fmtr Fmtr() {return fmtr;} private final Bry_fmtr fmtr = Bry_fmtr.new_(String_.Concat_lines_nl_skip_last
|
||||
|
||||
@@ -28,7 +28,7 @@ public class Xows_html_wkr_tst {
|
||||
fxt.Test_paging(Bool_.N, 0, " ");
|
||||
}
|
||||
@Test public void Rows() {
|
||||
fxt.Test_rows(Xows_db_row.Ary(fxt.Make_row(10, "A"), fxt.Make_row(20, "B")), String_.Concat_lines_nl_skip_last
|
||||
fxt.Test_rows(new Srch_rslt_itm[] {fxt.Make_row(10, "A"), fxt.Make_row(20, "B")}, String_.Concat_lines_nl_skip_last
|
||||
( ""
|
||||
, " <tr id='w.7CA'>"
|
||||
, " <td style='padding-right:5px; vertical-align:top; text-align:right;'>10"
|
||||
@@ -56,14 +56,14 @@ class Xows_html_wkr_fxt {
|
||||
return this;
|
||||
}
|
||||
public void Test_paging(boolean fwd, int paging_idx, String expd) {
|
||||
Xows_ui_qry qry = new Xows_ui_qry(Bry_.new_a7("A"), paging_idx, 100, Xosrh_rslt_itm_sorter.Tid_len_dsc, new Xows_ns_mgr(), true, new Xow_domain_itm[] {Xow_domain_itm_.parse(wiki.Domain_bry())});
|
||||
qry.Page_max_(2);
|
||||
Srch_qry qry = new Srch_qry(Bry_.new_a7("A"), paging_idx, 100, new Xows_ns_mgr(), true, new Xow_domain_itm[] {Xow_domain_itm_.parse(wiki.Domain_bry())});
|
||||
qry.page_max = 2;
|
||||
html_mgr.Init_by_wiki(wiki, wiki.Lang().Num_mgr(), qry);
|
||||
byte[] paging_link = html_mgr.Paging_link(fwd);
|
||||
Tfds.Eq(expd, String_.new_a7(paging_link));
|
||||
}
|
||||
public void Test_rows(Xows_db_row[] rows, String expd) {
|
||||
Xows_ui_rslt rslt = new Xows_ui_rslt();
|
||||
public void Test_rows(Srch_rslt_itm[] rows, String expd) {
|
||||
Srch_rslt_list rslt = new Srch_rslt_list();
|
||||
Xows_html_row html_row = new Xows_html_row(wiki.App().Html__lnki_bldr());
|
||||
html_row.Init(rslt);
|
||||
for (int i = 0; i < rows.length; ++i)
|
||||
@@ -71,8 +71,8 @@ class Xows_html_wkr_fxt {
|
||||
html_row.Bfr_arg__add(tmp_bfr);
|
||||
Tfds.Eq_str_lines(expd, tmp_bfr.To_str_and_clear());
|
||||
}
|
||||
public Xows_db_row Make_row(int len, String ttl_str) {
|
||||
public Srch_rslt_itm Make_row(int len, String ttl_str) {
|
||||
byte[] ttl_bry = Bry_.new_u8(ttl_str);
|
||||
return new Xows_db_row(Bry_.new_a7("w"), wiki.Ttl_parse(ttl_bry), 1, len);
|
||||
return new Srch_rslt_itm(Bry_.new_a7("w"), wiki.Ttl_parse(ttl_bry), 1, len);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -26,9 +26,9 @@ public class Xows_ns_mgr {
|
||||
ns_all = ns_main = false;
|
||||
}
|
||||
public boolean Has(int ns_id) {
|
||||
return ns_all // all flag set
|
||||
return ns_all // all flag set
|
||||
|| ns_main && ns_id == Xow_ns_.Tid__main // main flag set
|
||||
|| ns_hash.Has(tmp_ns_id.Val_(ns_id)) // check against ns_hash
|
||||
|| ns_hash.Has(tmp_ns_id.Val_(ns_id)) // check against ns_hash
|
||||
;
|
||||
}
|
||||
public void Add_by_id(int ns_id) {
|
||||
@@ -48,7 +48,7 @@ public class Xows_ns_mgr {
|
||||
int ns_enabled = Bry_.To_int_or_neg1(val);
|
||||
if (ns_enabled == 1) { // make sure set to 1; EX: ignore &ns0=0
|
||||
int key_len = key.length;
|
||||
if (key_len == 3 && key[2] == Byte_ascii.Star) // translate ns* as ns_all
|
||||
if (key_len == 3 && key[2] == Byte_ascii.Star) // translate ns* as ns_all
|
||||
ns_all = true;
|
||||
else {
|
||||
int ns_id = Bry_.To_int_or(key, 2, key_len, Int_.Min_value);
|
||||
|
||||
@@ -80,7 +80,7 @@ public class Xows_page__search implements Xows_page, GfoInvkAble, GfoEvObj {
|
||||
}
|
||||
page.Html_data().Html_restricted_n_();
|
||||
page.Html_data().Xtn_search_text_(search_bry);
|
||||
Xows_ui_qry qry = new Xows_ui_qry(search_bry, args_mgr.Paging_idx(), search_api.Results_per_page(), args_mgr.Sort_tid(), args_mgr.Ns_mgr(), search_api.Async_db(), search_domain_ary);
|
||||
Srch_qry qry = new Srch_qry(search_bry, args_mgr.Paging_idx(), search_api.Results_per_page(), args_mgr.Ns_mgr(), search_api.Async_db(), search_domain_ary);
|
||||
search_mgr.Search(wiki, page, qry);
|
||||
}
|
||||
// page found; return it;
|
||||
|
||||
@@ -17,27 +17,27 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.langs.htmls.*; import gplx.xowa.files.gui.*;
|
||||
class Xows_ui_async__html implements Xows_ui_async {
|
||||
class Xows_ui_async__html implements Srch_rslt_lnr {
|
||||
private final Xows_html_row html_row; private final Xog_js_wkr js_wkr;
|
||||
private final Xows_db_row[] rows; private final int rows_len;
|
||||
private final Srch_rslt_itm[] rows; private final int rows_len;
|
||||
private final Bry_bfr bfr = Bry_bfr.new_(255);
|
||||
private final byte[] insert_new_key;
|
||||
private final Cancelable cxl;
|
||||
public Xows_ui_async__html(Cancelable cxl, Xows_html_row html_row, Xog_js_wkr js_wkr, int paging_len, byte[] wiki) {
|
||||
this.cxl = cxl;
|
||||
this.html_row = html_row; this.js_wkr = js_wkr;
|
||||
this.rows = new Xows_db_row[paging_len];
|
||||
this.rows = new Srch_rslt_itm[paging_len];
|
||||
this.rows_len = paging_len;
|
||||
this.insert_new_key = Gen_insert_key(wiki);
|
||||
}
|
||||
public void Add(Xows_db_row new_row) {
|
||||
Xows_db_row last_row = rows[rows_len - 1];
|
||||
public void Notify_rslt_found(Srch_rslt_itm new_row) {
|
||||
Srch_rslt_itm last_row = rows[rows_len - 1];
|
||||
if (last_row != null) {
|
||||
if (Compare(new_row, last_row) == CompareAble_.MoreOrSame) return; // new_row is < last_row; exit
|
||||
}
|
||||
int new_row_slot = Find_insert_slot(new_row); if (new_row_slot == -1) return;
|
||||
Xows_db_row insert_row = rows[new_row_slot];
|
||||
byte[] insert_key = insert_row == null ? insert_new_key : insert_row.Key();
|
||||
Srch_rslt_itm insert_row = rows[new_row_slot];
|
||||
byte[] insert_key = insert_row == null ? insert_new_key : insert_row.key;
|
||||
Displace(new_row_slot, new_row);
|
||||
html_row.Gen_html(bfr, new_row);
|
||||
String html_tbl = bfr.To_str_and_clear();
|
||||
@@ -45,25 +45,25 @@ class Xows_ui_async__html implements Xows_ui_async {
|
||||
js_wkr.Html_elem_append_above(Gfh_utl.Encode_id_as_str(insert_key), html_tbl);
|
||||
if (last_row != null) {
|
||||
if (cxl.Canceled()) return;
|
||||
js_wkr.Html_elem_replace_html(Gfh_utl.Encode_id_as_str(last_row.Key()), "");
|
||||
js_wkr.Html_elem_replace_html(Gfh_utl.Encode_id_as_str(last_row.key), "");
|
||||
}
|
||||
}
|
||||
private int Find_insert_slot(Xows_db_row new_row) {
|
||||
private int Find_insert_slot(Srch_rslt_itm new_row) {
|
||||
for (int i = 0; i < rows_len; ++i) {
|
||||
Xows_db_row cur_row = rows[i];
|
||||
Srch_rslt_itm cur_row = rows[i];
|
||||
if (cur_row == null) return i;
|
||||
if (Compare(new_row, cur_row) == CompareAble_.Less) return i;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
private void Displace(int new_row_slot, Xows_db_row new_row) {
|
||||
private void Displace(int new_row_slot, Srch_rslt_itm new_row) {
|
||||
for (int i = rows_len - 2; i >= new_row_slot; --i) {
|
||||
rows[i + 1] = rows[i];
|
||||
}
|
||||
rows[new_row_slot] = new_row;
|
||||
}
|
||||
private int Compare(Xows_db_row lhs, Xows_db_row rhs) {
|
||||
return -Int_.Compare(lhs.Page_len(), rhs.Page_len());
|
||||
private int Compare(Srch_rslt_itm lhs, Srch_rslt_itm rhs) {
|
||||
return -Int_.Compare(lhs.page_len, rhs.page_len);
|
||||
}
|
||||
public static byte[] Gen_insert_key(byte[] wiki) {return Bry_.Add(Bry_insert_key, wiki);}
|
||||
private static final byte[] Bry_insert_key = Bry_.new_a7("xowa_insert_");
|
||||
|
||||
@@ -42,14 +42,14 @@ class Xows_ui_async_fxt {
|
||||
html_row.Fmtr().Fmt_("~{page_key}");
|
||||
async = new Xows_ui_async__html(Cancelable_.Never, html_row, js_wkr, 5, Bry_enwiki);
|
||||
}
|
||||
public Xows_db_row Make_rslt(int len, String ttl) {
|
||||
public Srch_rslt_itm Make_rslt(int len, String ttl) {
|
||||
byte[] ttl_bry = Bry_.new_a7(ttl);
|
||||
return new Xows_db_row(Bry_enwiki, wiki.Ttl_parse(ttl_bry), 1, len);
|
||||
return new Srch_rslt_itm(Bry_enwiki, wiki.Ttl_parse(ttl_bry), 1, len);
|
||||
}
|
||||
public Object[] Make_args_append(String uid, String html) {return Object_.Ary(Xog_js_wkr__log.Proc_append_above, uid, html);}
|
||||
public Object[] Make_args_replace(String uid) {return Object_.Ary(Xog_js_wkr__log.Proc_replace_html, uid, "");}
|
||||
public void Test_add(Xows_db_row row, Object[]... expd) {
|
||||
async.Add(row);
|
||||
public void Test_add(Srch_rslt_itm row, Object[]... expd) {
|
||||
async.Notify_rslt_found(row);
|
||||
int expd_len = expd.length;
|
||||
Tfds.Eq(expd_len, js_wkr.Log__len());
|
||||
for (int i = 0; i < expd_len; ++i) {
|
||||
|
||||
@@ -18,21 +18,21 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
package gplx.xowa.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.core.threads.*; import gplx.langs.htmls.*;
|
||||
import gplx.xowa.wikis.*; import gplx.xowa.files.gui.*; import gplx.xowa.guis.views.*;
|
||||
class Xows_ui_cmd implements GfoInvkAble, Cancelable, Xog_tab_close_lnr {
|
||||
private final Xows_core mgr; private final Xows_ui_qry qry; private final Xows_ui_rslt rslt;
|
||||
class Xows_ui_cmd implements GfoInvkAble, Cancelable, Srch_rslt_lnr, Xog_tab_close_lnr {
|
||||
private final Xows_core mgr; private final Srch_qry qry; private final Srch_rslt_list rslt;
|
||||
private final Xow_wiki wiki; private final Xoae_page page; private final Xog_tab_close_mgr tab_close_mgr; private final Xog_js_wkr js_wkr;
|
||||
private final boolean async; private Xows_ui_async async_wkr;
|
||||
private Xows_db_cache cache;
|
||||
public Xows_ui_cmd(Xows_core mgr, Xows_ui_qry qry, Xow_wiki wiki, Xoae_page page, Xog_tab_close_mgr tab_close_mgr, Xog_js_wkr js_wkr, Xows_db_cache cache, Xows_ui_async async_wkr) {
|
||||
private final boolean async; private Srch_rslt_lnr async_wkr;
|
||||
private Srch_rslt_hash cache;
|
||||
public Xows_ui_cmd(Xows_core mgr, Srch_qry qry, Xow_wiki wiki, Xoae_page page, Xog_tab_close_mgr tab_close_mgr, Xog_js_wkr js_wkr, Srch_rslt_hash cache, Srch_rslt_lnr async_wkr) {
|
||||
this.mgr = mgr; this.qry = qry; this.wiki = wiki; this.page = page; this.tab_close_mgr = tab_close_mgr; this.js_wkr = js_wkr; this.async_wkr = async_wkr;
|
||||
this.async = wiki.App().Mode().Tid_is_gui() && qry.Async_db();
|
||||
this.rslt = new Xows_ui_rslt();
|
||||
this.key = Gfh_utl.Encode_id_as_bry(Bry_.Add(qry.Key(), Byte_ascii.Pipe_bry, wiki.Domain_bry()));
|
||||
this.async = wiki.App().Mode().Tid_is_gui() && qry.async_db;
|
||||
this.rslt = new Srch_rslt_list();
|
||||
this.key = Gfh_utl.Encode_id_as_bry(Bry_.Add(qry.key, Byte_ascii.Pipe_bry, wiki.Domain_bry()));
|
||||
this.cache = cache;
|
||||
}
|
||||
public byte[] Key() {return key;} private final byte[] key;
|
||||
public Xow_wiki Wiki() {return wiki;}
|
||||
public Xows_ui_rslt Rslt() {return rslt;}
|
||||
public Srch_rslt_list Rslt() {return rslt;}
|
||||
public boolean Canceled() {return canceled;} private boolean canceled;
|
||||
public void Cancel() {
|
||||
Xoa_app_.Usr_dlg().Prog_many("", "", "search canceled: key=~{0}", key);
|
||||
@@ -43,10 +43,10 @@ class Xows_ui_cmd implements GfoInvkAble, Cancelable, Xog_tab_close_lnr {
|
||||
public boolean Search() {
|
||||
this.cache = mgr.Get_cache_or_new(key);
|
||||
boolean rv = false, fill_from_cache = true;
|
||||
if (!cache.Done() && (qry.Itms_end() > cache.Itms_end())) {
|
||||
if (!cache.Done() && (qry.itms_end > cache.Itms_end())) {
|
||||
if (async) {
|
||||
fill_from_cache = false; // NOTE: do not retrieve cached results to page, else ui_async cmd will add out of order; DATE:2015-04-24
|
||||
if (async_wkr == null) async_wkr = new Xows_ui_async__html(this, new Xows_html_row(new gplx.xowa.htmls.core.htmls.utls.Xoh_lnki_bldr(wiki.App(), wiki.App().Html__href_wtr())), js_wkr, qry.Page_len(), wiki.Domain_bry());
|
||||
if (async_wkr == null) async_wkr = new Xows_ui_async__html(this, new Xows_html_row(new gplx.xowa.htmls.core.htmls.utls.Xoh_lnki_bldr(wiki.App(), wiki.App().Html__href_wtr())), js_wkr, qry.page_len, wiki.Domain_bry());
|
||||
Thread_adp_.invk_(gplx.xowa.apps.Xoa_thread_.Key_special_search_db, this, Invk_search_db).Start();
|
||||
}
|
||||
else
|
||||
@@ -54,8 +54,8 @@ class Xows_ui_cmd implements GfoInvkAble, Cancelable, Xog_tab_close_lnr {
|
||||
rv = true;
|
||||
}
|
||||
if (fill_from_cache) {
|
||||
cache.Get_between(rslt, qry.Itms_bgn(), qry.Itms_end());
|
||||
qry.Page_max_(cache.Count() / qry.Page_len());
|
||||
cache.Get_between(rslt, qry.itms_bgn, qry.itms_end);
|
||||
qry.page_max = cache.Count() / qry.page_len;
|
||||
}
|
||||
return rv;
|
||||
}
|
||||
@@ -65,16 +65,16 @@ class Xows_ui_cmd implements GfoInvkAble, Cancelable, Xog_tab_close_lnr {
|
||||
while (!page.Html_data().Mode_wtxt_shown()) // NOTE:must check for wtxt_shown else async can happen first, and then be overwritten by wtxt; DATE:2015-04-26
|
||||
Thread_adp_.Sleep(100);
|
||||
// show any existing items in the cache on screen; new updates wil bump these off; SEE:NOTE:show_existing;DATE:2015-04-26
|
||||
int qry_itms_bgn = qry.Itms_bgn(), cache_count = cache.Count();
|
||||
int qry_itms_bgn = qry.itms_bgn, cache_count = cache.Count();
|
||||
for (int i = qry_itms_bgn; i < cache_count; ++i)
|
||||
async_wkr.Add(cache.Get_at(i));
|
||||
async_wkr.Notify_rslt_found(cache.Get_at(i));
|
||||
}
|
||||
new Xows_db_wkr().Search(this, this, qry, rslt, cache, wiki, wiki.Lang().Case_mgr());
|
||||
new Srch_db_wkr().Search(this, this, cache, wiki, wiki.Lang().Case_mgr(), qry);
|
||||
mgr.Search_end(this);
|
||||
if (this.Canceled()) return; // NOTE: must check else throws SWT exception
|
||||
this.Hide_cancel_btn();
|
||||
if (cache.Done())
|
||||
qry.Page_max_(cache.Count() / qry.Page_len());
|
||||
qry.page_max = cache.Count() / qry.page_len;
|
||||
Xoa_app_.Usr_dlg().Prog_many("", "", "");
|
||||
}
|
||||
private void Hide_cancel_btn() {
|
||||
@@ -83,9 +83,9 @@ class Xows_ui_cmd implements GfoInvkAble, Cancelable, Xog_tab_close_lnr {
|
||||
private void Hide_cancel_btn_async() {
|
||||
js_wkr.Html_atr_set("xowa_cancel_" + wiki.Domain_str(), "style", "display:none;");
|
||||
}
|
||||
public void Add_rslt(Xows_db_row rslt) {
|
||||
public void Notify_rslt_found(Srch_rslt_itm rslt) {
|
||||
cache.Add(rslt);
|
||||
if (async) async_wkr.Add(rslt);
|
||||
if (async) async_wkr.Notify_rslt_found(rslt);
|
||||
}
|
||||
public boolean When_close(Xog_tab_itm tab, Xoa_url url) {
|
||||
if (url != Xoa_url.Null) { // not called by close_tab (Ctrl+W)
|
||||
|
||||
@@ -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.specials.search; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*;
|
||||
import gplx.xowa.wikis.domains.*;
|
||||
class Xows_ui_qry {
|
||||
private final List_adp cmd_list = List_adp_.new_();
|
||||
public Xows_ui_qry(byte[] search_raw, int page_idx, int page_len, byte sort_tid, Xows_ns_mgr ns_mgr, boolean async_db, Xow_domain_itm[] wiki_domains) {
|
||||
this.search_raw = search_raw; this.page_idx = page_idx; this.page_len = page_len; this.sort_tid = sort_tid; this.ns_mgr = ns_mgr; this.async_db = async_db; this.wiki_domains = wiki_domains;
|
||||
this.itms_bgn = page_idx * page_len;
|
||||
this.page_max = page_idx; // default page_max to page_idx; adjust later when all results are known
|
||||
this.key = Bry_.Add_w_dlm(Byte_ascii.Pipe, search_raw, ns_mgr.To_hash_key());
|
||||
this.special_link_base_href = Bry_.Add(Bry_.new_a7("Special:Search/"), search_raw, Bry_.new_a7("?fulltext=y"));
|
||||
}
|
||||
public byte[] Key() {return key;} private final byte[] key;
|
||||
public byte[] Search_raw() {return search_raw;} private final byte[] search_raw;
|
||||
public boolean Async_db() {return async_db;} private boolean async_db;
|
||||
public int Page_idx() {return page_idx;} private final int page_idx;
|
||||
public int Page_max() {return page_max;} private int page_max;
|
||||
public int Page_len() {return page_len;} private final int page_len;
|
||||
public int Itms_bgn() {return itms_bgn;} private final int itms_bgn;
|
||||
public int Itms_end() {return itms_bgn + page_len;}
|
||||
public byte Sort_tid() {return sort_tid;} private final byte sort_tid;
|
||||
public Xows_ns_mgr Ns_mgr() {return ns_mgr;} private final Xows_ns_mgr ns_mgr;
|
||||
public Xow_domain_itm[] Wiki_domains() {return wiki_domains;} private final Xow_domain_itm[] wiki_domains;
|
||||
public void Page_max_(int v) {this.page_max = v;}
|
||||
public int Cmds__len() {return cmd_list.Count();}
|
||||
public Xows_ui_cmd Cmds__get_at(int i) {return (Xows_ui_cmd)cmd_list.Get_at(i);}
|
||||
public void Cmds__add(Xows_ui_cmd cmd) {cmd_list.Add(cmd);}
|
||||
public byte[] Special_link_base_href() {return special_link_base_href;} private final byte[] special_link_base_href;
|
||||
}
|
||||
@@ -0,0 +1,73 @@
|
||||
/*
|
||||
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.specials.search.crts; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*; import gplx.xowa.specials.search.*;
|
||||
import gplx.langs.regxs.*;
|
||||
public class Srch_crt_node {
|
||||
private final Gfo_pattern raw_pattern;
|
||||
public Srch_crt_node(int tid, byte[] raw, Srch_crt_node lhs, Srch_crt_node rhs) {
|
||||
this.tid = tid; this.raw = raw; this.lhs = lhs; this.rhs = rhs;
|
||||
this.raw_pattern = Bry_.Has(raw, Byte_ascii.Star) ? new Gfo_pattern(raw) : null;
|
||||
}
|
||||
public final int tid;
|
||||
public final byte[] raw;
|
||||
public final Srch_crt_node lhs;
|
||||
public final Srch_crt_node rhs;
|
||||
|
||||
public boolean Matches(gplx.xowa.langs.cases.Xol_case_mgr case_mgr, byte[] ttl) {
|
||||
byte[] ttl_lower = case_mgr.Case_build_lower(Xoa_ttl.Replace_unders(ttl));
|
||||
byte[][] ttl_words = Bry_split_.Split(ttl_lower, Byte_ascii.Space, Bool_.Y);
|
||||
return Matches(ttl_lower, ttl_words);
|
||||
}
|
||||
private boolean Matches(byte[] ttl_lower, byte[][] ttl_words) {
|
||||
switch (tid) {
|
||||
case Srch_crt_node.Tid_word: {
|
||||
int len = ttl_words.length;
|
||||
for (int i = 0; i < len; ++i) {
|
||||
byte[] word = ttl_words[i];
|
||||
if (raw_pattern == null) {
|
||||
if (Bry_.Eq(word, raw)) return true;
|
||||
}
|
||||
else {
|
||||
if (raw_pattern.Match(word)) return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
case Srch_crt_node.Tid_word_quote: // note that raw does not have quotes; EX: "B*" -> B*
|
||||
return Bry_find_.Find_fwd(ttl_lower, raw) != Bry_find_.Not_found;
|
||||
case Srch_crt_node.Tid_not:
|
||||
return !rhs.Matches(ttl_lower, ttl_words);
|
||||
case Srch_crt_node.Tid_or:
|
||||
return lhs.Matches(ttl_lower, ttl_words) || rhs.Matches(ttl_lower, ttl_words);
|
||||
case Srch_crt_node.Tid_and:
|
||||
return lhs.Matches(ttl_lower, ttl_words) && rhs.Matches(ttl_lower, ttl_words);
|
||||
case Srch_crt_node.Tid_null: return false;
|
||||
default: throw Err_.new_unhandled(tid);
|
||||
}
|
||||
}
|
||||
|
||||
public static final Srch_crt_node Null = new Srch_crt_node(Srch_crt_node.Tid_null, null, null, null);
|
||||
public static final int
|
||||
Tid_word = 0 // EX: 'A'
|
||||
, Tid_and = 1 // EX: 'A B'
|
||||
, Tid_or = 2 // EX: 'A OR B'
|
||||
, Tid_not = 3 // EX: '-A'
|
||||
, Tid_word_quote = 4 // EX: '"A B"'
|
||||
, Tid_null = 5
|
||||
;
|
||||
}
|
||||
@@ -0,0 +1,94 @@
|
||||
/*
|
||||
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.specials.search.crts; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*; import gplx.xowa.specials.search.*;
|
||||
public class Srch_crt_parser {
|
||||
private final Srch_parser_ctx parse_ctx = new Srch_parser_ctx(); private byte[] src;
|
||||
public Srch_crt_node Parse(byte[] src) {
|
||||
this.src = src;
|
||||
Srch_crt_tkn[] tkns = new Srch_crt_scanner().Scan(src);
|
||||
return Parse_itm_or(parse_ctx.Init(tkns));
|
||||
}
|
||||
private Srch_crt_node Parse_itm_or(Srch_parser_ctx parse_ctx) {
|
||||
Srch_crt_node lhs = Parse_itm_and(parse_ctx);
|
||||
while (parse_ctx.Cur_tid(Srch_crt_tkn.Tid_or)) {
|
||||
parse_ctx.Move_next();
|
||||
Srch_crt_node rhs = Parse_itm_and(parse_ctx);
|
||||
lhs = New_join(Srch_crt_node.Tid_or, lhs, rhs);
|
||||
}
|
||||
return lhs;
|
||||
}
|
||||
private Srch_crt_node Parse_itm_and(Srch_parser_ctx parse_ctx) {
|
||||
Srch_crt_node lhs = Parse_itm_not(parse_ctx);
|
||||
while (parse_ctx.Cur_tid(Srch_crt_tkn.Tid_and)) {
|
||||
parse_ctx.Move_next();
|
||||
Srch_crt_node rhs = Parse_itm_not(parse_ctx);
|
||||
lhs = New_join(Srch_crt_node.Tid_and, lhs, rhs);
|
||||
}
|
||||
return lhs;
|
||||
}
|
||||
private Srch_crt_node Parse_itm_not(Srch_parser_ctx parse_ctx) {
|
||||
Srch_crt_node lhs = Parse_itm_leaf(parse_ctx);
|
||||
while (parse_ctx.Cur_tid(Srch_crt_tkn.Tid_not)) {
|
||||
parse_ctx.Move_next();
|
||||
Srch_crt_node rhs = Parse_itm_leaf(parse_ctx);
|
||||
lhs = New_join(Srch_crt_node.Tid_not, null, rhs);
|
||||
}
|
||||
return lhs;
|
||||
}
|
||||
private Srch_crt_node Parse_itm_leaf(Srch_parser_ctx parse_ctx) {
|
||||
if (parse_ctx.Cur_tid(Srch_crt_tkn.Tid_paren_bgn)) {
|
||||
parse_ctx.Move_next();
|
||||
Srch_crt_node lhs = Parse_itm_or(parse_ctx);
|
||||
if (parse_ctx.Cur_tid(Srch_crt_tkn.Tid_paren_end)) parse_ctx.Move_next(); // skip token
|
||||
return lhs;
|
||||
}
|
||||
else if (parse_ctx.Cur_tid(Srch_crt_tkn.Tid_eos))
|
||||
return Srch_crt_node.Null;
|
||||
else {
|
||||
Srch_crt_tkn word_tkn = parse_ctx.Move_next();
|
||||
if (word_tkn.tid == Srch_crt_tkn.Tid_not) {
|
||||
word_tkn = parse_ctx.Move_next();
|
||||
if (word_tkn == null) return Srch_crt_node.Null; // occurs in "a -"
|
||||
Srch_crt_node word_itm = New_word(word_tkn, src);
|
||||
return New_join(Srch_crt_node.Tid_not, null, word_itm);
|
||||
}
|
||||
else
|
||||
return New_word(word_tkn, src);
|
||||
}
|
||||
}
|
||||
private static Srch_crt_node New_word(Srch_crt_tkn tkn, byte[] src) {
|
||||
int tid = tkn.tid == Srch_crt_tkn.Tid_word ? Srch_crt_node.Tid_word : Srch_crt_node.Tid_word_quote;
|
||||
return new Srch_crt_node(tid, tkn.val, null, null);
|
||||
}
|
||||
private static Srch_crt_node New_join(int tid, Srch_crt_node lhs, Srch_crt_node rhs) {return new Srch_crt_node(tid, null, lhs, rhs);}
|
||||
}
|
||||
class Srch_parser_ctx {
|
||||
private Srch_crt_tkn[] ary; private int pos = 0; private int ary_len;
|
||||
public Srch_parser_ctx Init(Srch_crt_tkn[] ary) {
|
||||
this.ary = ary;
|
||||
this.ary_len = ary.length;
|
||||
this.pos = 0;
|
||||
return this;
|
||||
}
|
||||
public boolean Cur_tid(byte tid) {return pos < ary_len ? tid == ary[pos].tid : tid == Srch_crt_tkn.Tid_eos;}
|
||||
public Srch_crt_tkn Move_next() {
|
||||
Srch_crt_tkn rv = null;
|
||||
if (pos < ary_len) rv = ary[pos++];
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
@@ -15,12 +15,12 @@ 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.specials.search.parsers_old; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*; import gplx.xowa.specials.search.*;
|
||||
package gplx.xowa.specials.search.crts; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*; import gplx.xowa.specials.search.*;
|
||||
import gplx.core.primitives.*; import gplx.core.btries.*;
|
||||
class Xow_search_scanner {
|
||||
class Srch_crt_scanner {
|
||||
private final List_adp tkns = List_adp_.new_(); private byte[] src; private int src_len, pos, txt_bgn;
|
||||
private final Ordered_hash tmp_list = Ordered_hash_.New(); private final Bry_bfr tmp_bfr = Bry_bfr.new_();
|
||||
public Xow_search_tkn[] Scan(byte[] src) {
|
||||
public Srch_crt_tkn[] Scan(byte[] src) {
|
||||
this.src = src; this.src_len = src.length;
|
||||
tkns.Clear(); pos = 0; txt_bgn = -1;
|
||||
while (pos < src_len) {
|
||||
@@ -35,27 +35,27 @@ class Xow_search_scanner {
|
||||
byte cur_tid = ((Byte_obj_val)cur_obj).Val();
|
||||
if (Cur_join_is_word(cur_tid, pos_end)) continue; // ignore words containing "and", "or"; EX: "random"; "for"
|
||||
if (txt_bgn != -1) { // pending word; create
|
||||
Tkns_add_word(Xow_search_tkn.Tid_word, txt_bgn, pos);
|
||||
Tkns_add_word(Srch_crt_tkn.Tid_word, txt_bgn, pos);
|
||||
txt_bgn = -1;
|
||||
}
|
||||
switch (cur_tid) {
|
||||
case Xow_search_tkn.Tid_space: // discard spaces
|
||||
case Srch_crt_tkn.Tid_space: // discard spaces
|
||||
pos = Bry_find_.Find_fwd_while(src, pos, src_len, Byte_ascii.Space);
|
||||
break;
|
||||
case Xow_search_tkn.Tid_quote: // find end quote and add as word
|
||||
case Srch_crt_tkn.Tid_quote: // find end quote and add as word
|
||||
int quote_bgn = pos + 1;
|
||||
int quote_end = Bry_find_.Find_fwd(src, Byte_ascii.Quote, quote_bgn, src_len);
|
||||
if (quote_end == Bry_find_.Not_found) throw Err_.new_wo_type("could not find end quote", "src", String_.new_u8(src));
|
||||
Tkns_add_word(Xow_search_tkn.Tid_word_quoted, quote_bgn, quote_end);
|
||||
Tkns_add_word(Srch_crt_tkn.Tid_word_quoted, quote_bgn, quote_end);
|
||||
pos = quote_end + 1; // +1 to place after quote
|
||||
break;
|
||||
case Xow_search_tkn.Tid_not:
|
||||
Tkns_add_word(Xow_search_tkn.Tid_not, pos, pos_end);
|
||||
case Srch_crt_tkn.Tid_not:
|
||||
Tkns_add_word(Srch_crt_tkn.Tid_not, pos, pos_end);
|
||||
pos = pos_end;
|
||||
break;
|
||||
case Xow_search_tkn.Tid_paren_bgn: case Xow_search_tkn.Tid_paren_end:
|
||||
case Xow_search_tkn.Tid_and: case Xow_search_tkn.Tid_or:
|
||||
tkns.Add(new_tkn(cur_tid, pos, pos_end));
|
||||
case Srch_crt_tkn.Tid_paren_bgn: case Srch_crt_tkn.Tid_paren_end:
|
||||
case Srch_crt_tkn.Tid_and: case Srch_crt_tkn.Tid_or:
|
||||
tkns.Add(new_tkn(cur_tid, src, pos, pos_end));
|
||||
pos = pos_end;
|
||||
break;
|
||||
default: throw Err_.new_unhandled(cur_tid);
|
||||
@@ -63,20 +63,20 @@ class Xow_search_scanner {
|
||||
}
|
||||
}
|
||||
if (txt_bgn != -1) { // pending word; create
|
||||
Tkns_add_word(Xow_search_tkn.Tid_word, txt_bgn, pos);
|
||||
Tkns_add_word(Srch_crt_tkn.Tid_word, txt_bgn, pos);
|
||||
txt_bgn = -1;
|
||||
}
|
||||
return (Xow_search_tkn[])tkns.To_ary_and_clear(Xow_search_tkn.class);
|
||||
return (Srch_crt_tkn[])tkns.To_ary_and_clear(Srch_crt_tkn.class);
|
||||
}
|
||||
private boolean Cur_join_is_word(byte cur_tid, int pos_end) { // extra logic to handle and / or occuring in unquoted strings; EX: "random"; "for"
|
||||
switch (cur_tid) {
|
||||
default: return false; // only look at AND, OR, -
|
||||
case Xow_search_tkn.Tid_and: case Xow_search_tkn.Tid_or: case Xow_search_tkn.Tid_not:
|
||||
case Srch_crt_tkn.Tid_and: case Srch_crt_tkn.Tid_or: case Srch_crt_tkn.Tid_not:
|
||||
break;
|
||||
}
|
||||
boolean join_is_word = true;
|
||||
if (txt_bgn == -1) { // no pending word;
|
||||
if (cur_tid == Xow_search_tkn.Tid_not) return false; // NOT is only operator if no pending tkn; EX: -abc -> NOT abc; a-b -> a-b
|
||||
if (cur_tid == Srch_crt_tkn.Tid_not) return false; // NOT is only operator if no pending tkn; EX: -abc -> NOT abc; a-b -> a-b
|
||||
byte nxt_b = pos_end < src_len ? src[pos_end] : Byte_ascii.Null;
|
||||
Object nxt_obj = trie.Match_bgn_w_byte(nxt_b, src, pos_end, src_len);
|
||||
if (nxt_obj == null) // next tkn is text; join must be word
|
||||
@@ -84,11 +84,11 @@ class Xow_search_scanner {
|
||||
else { // next tkn is tkn
|
||||
byte nxt_tid = ((Byte_obj_val)nxt_obj).Val();
|
||||
switch (nxt_tid) {
|
||||
case Xow_search_tkn.Tid_space: case Xow_search_tkn.Tid_quote:
|
||||
case Xow_search_tkn.Tid_paren_bgn: case Xow_search_tkn.Tid_paren_end:
|
||||
case Srch_crt_tkn.Tid_space: case Srch_crt_tkn.Tid_quote:
|
||||
case Srch_crt_tkn.Tid_paren_bgn: case Srch_crt_tkn.Tid_paren_end:
|
||||
join_is_word = false; // next tkn is sym; and/or is not word; EX: a AND ; a AND"b"; a AND(b)
|
||||
break;
|
||||
case Xow_search_tkn.Tid_not: case Xow_search_tkn.Tid_and: case Xow_search_tkn.Tid_or:
|
||||
case Srch_crt_tkn.Tid_not: case Srch_crt_tkn.Tid_and: case Srch_crt_tkn.Tid_or:
|
||||
join_is_word = true; // next tkn is and or not; and/or is word; EX: andor; oror; or-abc;
|
||||
break;
|
||||
default: throw Err_.new_unhandled(cur_tid);
|
||||
@@ -104,18 +104,18 @@ class Xow_search_scanner {
|
||||
return true;
|
||||
}
|
||||
if (txt_bgn != -1) {
|
||||
Tkns_add_word(Xow_search_tkn.Tid_word, txt_bgn, pos); // create word
|
||||
Tkns_add_word(Srch_crt_tkn.Tid_word, txt_bgn, pos); // create word
|
||||
txt_bgn = -1;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
private void Tkns_add_word(byte tid, int src_bgn, int src_end) {
|
||||
if (tkns.Count() > 0) { // at least 1 tkn; check for "auto-and"
|
||||
Xow_search_tkn last_tkn = (Xow_search_tkn)tkns.Get_at_last();
|
||||
if (last_tkn.Tid() == Xow_search_tkn.Tid_word) // previous tkn is word; auto "AND" words; EX: A B -> A AND B
|
||||
tkns.Add(Xow_search_tkn.new_bry(Xow_search_tkn.Tid_and, Bry_and));
|
||||
Srch_crt_tkn last_tkn = (Srch_crt_tkn)tkns.Get_at_last();
|
||||
if (last_tkn.tid == Srch_crt_tkn.Tid_word) // previous tkn is word; auto "AND" words; EX: A B -> A AND B
|
||||
tkns.Add(new Srch_crt_tkn(Srch_crt_tkn.Tid_and, Bry_and));
|
||||
}
|
||||
if (tid == Xow_search_tkn.Tid_word) { // if word has symbol, convert to quoted; EX: a-b should become "a-b"; otherwise searcher would search for a single word a-b
|
||||
if (tid == Srch_crt_tkn.Tid_word) { // if word has symbol, convert to quoted; EX: a-b should become "a-b"; otherwise searcher would search for a single word a-b
|
||||
byte[] cur_word = Bry_.Mid(src, src_bgn, src_end);
|
||||
byte[][] words = gplx.xowa.bldrs.cmds.texts.Xob_search_base.Split_ttl_into_words(null, tmp_list, tmp_bfr, cur_word);
|
||||
int words_len = words.length;
|
||||
@@ -123,22 +123,22 @@ class Xow_search_scanner {
|
||||
&& !Bry_.Eq(words[0], cur_word) // split word not same as raw
|
||||
&& Bry_find_.Find_fwd(cur_word, Byte_ascii.Star) == -1 // no asterisk
|
||||
) {
|
||||
tkns.Add(Xow_search_tkn.new_bry(tid, words[0]));
|
||||
tkns.Add(new Srch_crt_tkn(tid, words[0]));
|
||||
return;
|
||||
}
|
||||
if (words.length > 1) // multiple words; add as quoted-term; EX: "a-b"
|
||||
tid = Xow_search_tkn.Tid_word_quoted;
|
||||
tid = Srch_crt_tkn.Tid_word_quoted;
|
||||
}
|
||||
tkns.Add(new_tkn(tid, src_bgn, src_end));
|
||||
tkns.Add(new_tkn(tid, src, src_bgn, src_end));
|
||||
}
|
||||
private Xow_search_tkn new_tkn(byte tid, int val_bgn, int val_end) {return Xow_search_tkn.new_pos(tid, val_bgn, val_end);}
|
||||
private Srch_crt_tkn new_tkn(byte tid, byte[] src, int val_bgn, int val_end) {return new Srch_crt_tkn(tid, Bry_.Mid(src, val_bgn, val_end));}
|
||||
private static final byte[] Bry_and = Bry_.new_a7("AND");
|
||||
private static final Btrie_slim_mgr trie = Btrie_slim_mgr.ci_a7()// NOTE:ci.ascii:OR / AND only
|
||||
.Add_str_byte(" " , Xow_search_tkn.Tid_space)
|
||||
.Add_str_byte("\"" , Xow_search_tkn.Tid_quote)
|
||||
.Add_str_byte("-" , Xow_search_tkn.Tid_not)
|
||||
.Add_str_byte("(" , Xow_search_tkn.Tid_paren_bgn)
|
||||
.Add_str_byte(")" , Xow_search_tkn.Tid_paren_end)
|
||||
.Add_str_byte("or" , Xow_search_tkn.Tid_or)
|
||||
.Add_str_byte("and" , Xow_search_tkn.Tid_and);
|
||||
.Add_str_byte(" " , Srch_crt_tkn.Tid_space)
|
||||
.Add_str_byte("\"" , Srch_crt_tkn.Tid_quote)
|
||||
.Add_str_byte("-" , Srch_crt_tkn.Tid_not)
|
||||
.Add_str_byte("(" , Srch_crt_tkn.Tid_paren_bgn)
|
||||
.Add_str_byte(")" , Srch_crt_tkn.Tid_paren_end)
|
||||
.Add_str_byte("or" , Srch_crt_tkn.Tid_or)
|
||||
.Add_str_byte("and" , Srch_crt_tkn.Tid_and);
|
||||
}
|
||||
@@ -15,11 +15,23 @@ 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.specials.search.quicks; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*; import gplx.xowa.specials.search.*;
|
||||
public class Xoa_search_mgr {
|
||||
public Xoa_search_itm[] Search(byte[] search) {
|
||||
// page_title LIKE 'Ear%'
|
||||
// page_title LIKE '%Ear%'
|
||||
return null;
|
||||
}
|
||||
package gplx.xowa.specials.search.crts; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*; import gplx.xowa.specials.search.*;
|
||||
class Srch_crt_tkn {
|
||||
public final byte tid;
|
||||
public final byte[] val;
|
||||
public Srch_crt_tkn(byte tid, byte[] val) {this.tid = tid; this.val = val;}
|
||||
|
||||
public static final byte
|
||||
Tid_root = 1
|
||||
, Tid_word = 2
|
||||
, Tid_word_quoted = 3
|
||||
, Tid_space = 4
|
||||
, Tid_quote = 5
|
||||
, Tid_not = 6
|
||||
, Tid_paren_bgn = 7
|
||||
, Tid_paren_end = 8
|
||||
, Tid_or = 9
|
||||
, Tid_and = 10
|
||||
, Tid_eos = 11
|
||||
;
|
||||
}
|
||||
80
400_xowa/src/gplx/xowa/specials/search/dbs/Srch_db_mgr.java
Normal file
80
400_xowa/src/gplx/xowa/specials/search/dbs/Srch_db_mgr.java
Normal file
@@ -0,0 +1,80 @@
|
||||
/*
|
||||
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/>.
|
||||
*/
|
||||
//namespace gplx.xowa.specials.search.dbs {
|
||||
// using gplx.dbs; using gplx.xowa.wikis.data.tbls;
|
||||
// using gplx.xowa.langs.cases; using gplx.xowa.wikis.nss;
|
||||
// // workset_count
|
||||
// // workset_score_min
|
||||
// class Srch_db_mgr {
|
||||
// private Srch_word_tbl srch_word_tbl = new Srch_word_tbl(null, null);
|
||||
// private Srch_page_tbl srch_page_tbl = new Srch_page_tbl();
|
||||
// private Page_tbl page_tbl = new Page_tbl();
|
||||
// public void Search(Srch_request req) {
|
||||
// List_adp results = req.results;
|
||||
// int curr = results.Count();
|
||||
// int need = curr + req.req__count;
|
||||
// while (curr < need) {
|
||||
// // foreach (word)
|
||||
// srch_word_tbl.Get(req, null); // read words
|
||||
// srch_page_tbl.Get(req); // get pages for every words
|
||||
// // add to potential results; skip if failed and / not (but can't do quote)
|
||||
// page_tbl.Get(req); // get actual page and check for ns; quote; redirect
|
||||
// // repeat until matched
|
||||
// need = results.Count();
|
||||
// }
|
||||
// }
|
||||
// // get all pages in word_id set sorted by page_search_score
|
||||
// // stop if
|
||||
// // - no more pages; normal case
|
||||
// // - page_score < workset_score_min; case with many pages (1000 pages)
|
||||
//// private int Get_word_id_pages
|
||||
//// ( Cancelable cancelable, Xow_wiki wiki, Xol_case_mgr case_mgr
|
||||
//// , Srch_request req, Xows_ui_cmd cmd, Srch_qry qry, Srch_rslt_hash cache
|
||||
//// , Db_attach_rdr attach_rdr, String sql, Xowd_page_tbl page_tbl
|
||||
//// , Srch_word_row word, Srch_crt_node matcher, int rslts_wanted, int workset_score_min) {
|
||||
//// int rslts_found = 0;
|
||||
//// Xow_ns_mgr ns_mgr = wiki.Ns_mgr();
|
||||
//// Db_rdr rdr = attach_rdr.Exec_as_rdr(sql);
|
||||
//// try {
|
||||
//// while (rdr.Move_next()) {
|
||||
//// if (cancelable.Canceled()) return -1;
|
||||
//// word.Rslts_offset_add_1();
|
||||
//// int page_ns = rdr.Read_int(page_tbl.Fld_page_ns());
|
||||
//// if (!qry.Ns_mgr().Has(page_ns)) continue; // ignore: ns doesn't match
|
||||
//// byte[] page_ttl = rdr.Read_bry_by_str(page_tbl.Fld_page_title());
|
||||
//// // Io_mgr.Instance.AppendFilStr("C:\\temp.txt", String_.new_u8(word.Text()) + "|" + Int_.To_str(page_ns) + "|" + String_.new_u8(page_ttl) + "\n");
|
||||
//// byte[] page_ttl_lc = case_mgr.Case_build_lower(Xoa_ttl.Replace_unders(page_ttl));
|
||||
//// byte[][] page_ttl_words = Bry_split_.Split(page_ttl_lc, Byte_ascii.Space, Bool_.Y);
|
||||
//// if (!matcher.Matches(page_ttl_lc, page_ttl_words)) continue; // ignore: ttl doesn't match matcher
|
||||
//// int page_id = rdr.Read_int(page_tbl.Fld_page_id());
|
||||
//// int page_len = rdr.Read_int(page_tbl.Fld_page_len());
|
||||
//// int page_link_score = 0; //rdr.Read_int(page_tbl.Fld_page_link_score());
|
||||
//// Xow_ns ns = ns_mgr.Ids_get_or_null(page_ns);
|
||||
//// byte[] page_ttl_w_ns = ns.Gen_ttl(page_ttl);
|
||||
//// if (cache.Has(page_ttl_w_ns)) continue; // ignore: page already added by another word; EX: "A B"; word is "B", but "A B" already added by "A"
|
||||
//// Xoa_ttl ttl = wiki.Ttl_parse(page_ttl_w_ns);
|
||||
//// Srch_rslt_itm row = new Srch_rslt_itm(wiki.Domain_bry(), ttl, page_id, page_len);
|
||||
//// cmd.Add_rslt(row);
|
||||
//// if (++rslts_found == rslts_wanted) break; // stop: found enough results; DATE:2015-04-24
|
||||
//// }
|
||||
//// } finally {rdr.Rls();}
|
||||
//// if (rslts_found == 0) word.Rslts_done_y_(); // read through entire rdr and nothing found; mark word done
|
||||
//// return rslts_found;
|
||||
//// }
|
||||
// }
|
||||
//}
|
||||
125
400_xowa/src/gplx/xowa/specials/search/dbs/Srch_word_row.java
Normal file
125
400_xowa/src/gplx/xowa/specials/search/dbs/Srch_word_row.java
Normal file
@@ -0,0 +1,125 @@
|
||||
/*
|
||||
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/>.
|
||||
*/
|
||||
//namespace gplx.xowa.specials.search.dbs {
|
||||
// using gplx.dbs; using gplx.xowa.wikis.data.tbls;
|
||||
// // a
|
||||
// // a b
|
||||
// // a*
|
||||
// class Srch_word_tbl {
|
||||
// private final Db_conn conn;
|
||||
// private final Xowd_search_word_tbl tbl;
|
||||
// public Srch_word_tbl(Db_conn conn, Xowd_search_word_tbl tbl) {this.conn = conn; this.tbl = tbl;}
|
||||
// public void Get(Srch_request req, Srch_cache_word cache_word) {
|
||||
// // int req_count = req.req__count;
|
||||
// // conn.Stmt_select_order(tbl.Tbl_name(), String_.Ary(tbl.Fld_id(), tbl.Fld_w()));
|
||||
// // SELECT word_id, word_text FROM search_word WHERE word_text LIKE "~{word}%" AND word_text > '' ORDER BY word_page_score DESC OFFSET 0;
|
||||
// Db_qry qry = Db_qry_.select_()
|
||||
// .From_(tbl.Tbl_name())
|
||||
// .Cols_(tbl.Fld_id(), tbl.Fld_text(), tbl.Fld_page_count(), tbl.Fld_page_score_max())
|
||||
// .Where_(Db_crt_.New_like(tbl.Fld_text(), ""))
|
||||
// .OrderBy_(tbl.Fld_page_score_max(), false)
|
||||
// // .Offset_();
|
||||
// ;
|
||||
// Db_stmt stmt = conn.Stmt_new(qry);
|
||||
// stmt.Clear().Crt_str(tbl.Fld_text(), req.search);
|
||||
// Db_rdr rdr = stmt.Exec_select__rls_auto();
|
||||
// int cur_count = 0;
|
||||
// while (rdr.Move_next()) {
|
||||
// int word_id = rdr.Read_int(tbl.Fld_id());
|
||||
// byte[] word_text = rdr.Read_bry_by_str(tbl.Fld_text());
|
||||
// int page_count = rdr.Read_int(tbl.Fld_page_count());
|
||||
// int page_score_max = rdr.Read_int(tbl.Fld_page_score_max());
|
||||
// Srch_word_row row = new Srch_word_row(word_id, word_text, page_count, page_score_max);
|
||||
// cache_word.words.Add(row);
|
||||
// cur_count += page_count;
|
||||
// ++cache_word.offset;
|
||||
// if (cur_count >= (req.req__count * 2)) break;
|
||||
// }
|
||||
// /*
|
||||
// Get_rng; now in set of 100, scores may range from 1234 to 50; search every word to get minimum
|
||||
// */
|
||||
// }
|
||||
// }
|
||||
// class Srch_page_tbl {
|
||||
// public void Get(Srch_request req) {
|
||||
// }
|
||||
// }
|
||||
// class Page_tbl {
|
||||
// public void Get(Srch_request req) {}
|
||||
// }
|
||||
// class Srch_word_row {
|
||||
// public int word_id;
|
||||
// public byte[] text;
|
||||
// public int page_count;
|
||||
// public int page_score_max;
|
||||
// public int rslts_offset;
|
||||
// public boolean rslts_done;
|
||||
// public Srch_word_row(int word_id, byte[] text, int page_count, int page_score_max) {
|
||||
// this.word_id = word_id; this.text = text; this.page_count = page_count; this.page_score_max = page_score_max;
|
||||
// rslts_offset = 0; rslts_done = false;
|
||||
// }
|
||||
// public void Rslts_offset_add_1() {++rslts_offset;}
|
||||
// public void Rslts_done_y_() {rslts_done = true;}
|
||||
// }
|
||||
// class Srch_page_row {
|
||||
// public int word_id;
|
||||
// public int page_id;
|
||||
// public void Load(int word_id, int page_id) {
|
||||
// this.word_id = word_id; this.page_id = page_id;
|
||||
// }
|
||||
// }
|
||||
// class Srch_cache_word {
|
||||
// public byte[] search;
|
||||
// public final List_adp words = List_adp_.new_();
|
||||
// public int offset;
|
||||
// public void Init_new(byte[] search) {
|
||||
// this.search = search;
|
||||
// words.Clear();
|
||||
// offset = 0;
|
||||
// }
|
||||
// }
|
||||
// class Srch_request {
|
||||
// public String search;
|
||||
// public int req__count;
|
||||
// public boolean wildcard;
|
||||
// public String bmk__word__text;
|
||||
// public int bmk__page__word_id;
|
||||
// public int bmk__page__page_id;
|
||||
// // all_pages;
|
||||
// // view_pages
|
||||
// public final List_adp results = List_adp_.new_();
|
||||
// public final Srch_cache_word tbl__word = new Srch_cache_word();
|
||||
// public void Init_new(String search, boolean wildcard, int req__count) {
|
||||
// this.search = search; this.wildcard = wildcard; this.req__count = req__count;
|
||||
// this.bmk__word__text = "";
|
||||
// this.bmk__page__word_id = -1;
|
||||
// this.bmk__page__page_id = -1;
|
||||
// tbl__word.Init_new(Bry_.new_a7(search));
|
||||
// results.Clear();
|
||||
// }
|
||||
// public void Init_continue(int req__count) {
|
||||
// }
|
||||
// }
|
||||
// class Srch_query {
|
||||
// public String raw;
|
||||
// public Srch_query(String raw) {
|
||||
// this.raw = raw;
|
||||
// // separate to words
|
||||
// }
|
||||
// }
|
||||
//}
|
||||
@@ -1,94 +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.specials.search.parsers_old; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*; import gplx.xowa.specials.search.*;
|
||||
public class Xow_search_parser {
|
||||
private Xow_search_parser_ctx parse_ctx = new Xow_search_parser_ctx(); private byte[] src;
|
||||
public Xows_db_matcher Parse(byte[] src) {
|
||||
this.src = src;
|
||||
Xow_search_tkn[] tkns = new Xow_search_scanner().Scan(src);
|
||||
return Parse_itm_or(parse_ctx.Init(tkns));
|
||||
}
|
||||
private Xows_db_matcher Parse_itm_or(Xow_search_parser_ctx parse_ctx) {
|
||||
Xows_db_matcher lhs = Parse_itm_and(parse_ctx);
|
||||
while (parse_ctx.Cur_tid(Xow_search_tkn.Tid_or)) {
|
||||
parse_ctx.Move_next();
|
||||
Xows_db_matcher rhs = Parse_itm_and(parse_ctx);
|
||||
lhs = new_join(Xows_db_matcher.Tid_or, lhs, rhs);
|
||||
}
|
||||
return lhs;
|
||||
}
|
||||
private Xows_db_matcher Parse_itm_and(Xow_search_parser_ctx parse_ctx) {
|
||||
Xows_db_matcher lhs = Parse_itm_not(parse_ctx);
|
||||
while (parse_ctx.Cur_tid(Xow_search_tkn.Tid_and)) {
|
||||
parse_ctx.Move_next();
|
||||
Xows_db_matcher rhs = Parse_itm_not(parse_ctx);
|
||||
lhs = new_join(Xows_db_matcher.Tid_and, lhs, rhs);
|
||||
}
|
||||
return lhs;
|
||||
}
|
||||
private Xows_db_matcher Parse_itm_not(Xow_search_parser_ctx parse_ctx) {
|
||||
Xows_db_matcher lhs = Parse_itm_leaf(parse_ctx);
|
||||
while (parse_ctx.Cur_tid(Xow_search_tkn.Tid_not)) {
|
||||
parse_ctx.Move_next();
|
||||
Xows_db_matcher rhs = Parse_itm_leaf(parse_ctx);
|
||||
lhs = new_join(Xows_db_matcher.Tid_not, null, rhs);
|
||||
}
|
||||
return lhs;
|
||||
}
|
||||
private Xows_db_matcher Parse_itm_leaf(Xow_search_parser_ctx parse_ctx) {
|
||||
if (parse_ctx.Cur_tid(Xow_search_tkn.Tid_paren_bgn)) {
|
||||
parse_ctx.Move_next();
|
||||
Xows_db_matcher lhs = Parse_itm_or(parse_ctx);
|
||||
if (parse_ctx.Cur_tid(Xow_search_tkn.Tid_paren_end)) parse_ctx.Move_next(); // skip token
|
||||
return lhs;
|
||||
}
|
||||
else if (parse_ctx.Cur_tid(Xow_search_tkn.Tid_eos))
|
||||
return Xows_db_matcher.Null;
|
||||
else {
|
||||
Xow_search_tkn word_tkn = parse_ctx.Move_next();
|
||||
if (word_tkn.Tid() == Xow_search_tkn.Tid_not) {
|
||||
word_tkn = parse_ctx.Move_next();
|
||||
if (word_tkn == null) return Xows_db_matcher.Null; // occurs in "a -"
|
||||
Xows_db_matcher word_itm = new_word(word_tkn, src);
|
||||
return new_join(Xows_db_matcher.Tid_not, null, word_itm);
|
||||
}
|
||||
else
|
||||
return new_word(word_tkn, src);
|
||||
}
|
||||
}
|
||||
private static Xows_db_matcher new_word(Xow_search_tkn tkn, byte[] src) {
|
||||
int tid = tkn.Tid() == Xow_search_tkn.Tid_word ? Xows_db_matcher.Tid_word : Xows_db_matcher.Tid_word_quote;
|
||||
return new Xows_db_matcher(tid, tkn.Val(src), null, null);
|
||||
}
|
||||
private static Xows_db_matcher new_join(int tid, Xows_db_matcher lhs, Xows_db_matcher rhs) {return new Xows_db_matcher(tid, null, lhs, rhs);}
|
||||
}
|
||||
class Xow_search_parser_ctx {
|
||||
private Xow_search_tkn[] ary; private int pos = 0; private int ary_len;
|
||||
public Xow_search_parser_ctx Init(Xow_search_tkn[] ary) {
|
||||
this.ary = ary;
|
||||
this.ary_len = ary.length;
|
||||
this.pos = 0;
|
||||
return this;
|
||||
}
|
||||
public boolean Cur_tid(byte tid) {return pos < ary_len ? tid == ary[pos].Tid(): tid == Xow_search_tkn.Tid_eos;}
|
||||
public Xow_search_tkn Move_next() {
|
||||
Xow_search_tkn rv = null;
|
||||
if (pos < ary_len) rv = ary[pos++];
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
@@ -1,40 +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.specials.search.parsers_old; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*; import gplx.xowa.specials.search.*;
|
||||
class Xow_search_tkn {
|
||||
private final int val_bgn, val_end;
|
||||
private final byte[] val_bry;
|
||||
Xow_search_tkn(byte tid, int val_bgn, int val_end, byte[] val_bry) {this.tid = tid; this.val_bgn = val_bgn; this.val_end = val_end; this.val_bry = val_bry;}
|
||||
public byte Tid() {return tid;} private final byte tid;
|
||||
public byte[] Val(byte[] src) {return val_bry == null ? Bry_.Mid(src, val_bgn, val_end) : val_bry;}
|
||||
public static Xow_search_tkn new_pos(byte tid, int val_bgn, int val_end) {return new Xow_search_tkn(tid, val_bgn, val_end, null);}
|
||||
public static Xow_search_tkn new_bry(byte tid, byte[] val_bry) {return new Xow_search_tkn(tid, -1, -1, val_bry);}
|
||||
public static final byte
|
||||
Tid_root = 1
|
||||
, Tid_word = 2
|
||||
, Tid_word_quoted = 3
|
||||
, Tid_space = 4
|
||||
, Tid_quote = 5
|
||||
, Tid_not = 6
|
||||
, Tid_paren_bgn = 7
|
||||
, Tid_paren_end = 8
|
||||
, Tid_or = 9
|
||||
, Tid_and = 10
|
||||
, Tid_eos = 11
|
||||
;
|
||||
}
|
||||
@@ -1,27 +0,0 @@
|
||||
/*
|
||||
XOWA: the XOWA Offline Wiki Application
|
||||
Copyright (C) 2012 gnosygnu@gmail.com
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the
|
||||
License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package gplx.xowa.specials.search.quicks; import gplx.*; import gplx.xowa.*; import gplx.xowa.specials.*; import gplx.xowa.specials.search.*;
|
||||
public class Xoa_search_itm {
|
||||
public Xoa_search_itm(byte[] url, byte[] name, byte[] descrip, byte[] img) {
|
||||
this.url = url; this.name = name; this.descrip = descrip; this.img = img;
|
||||
}
|
||||
public byte[] Url() {return url;} private final byte[] url; // EX: en.wikipedia.org/wiki/Earth
|
||||
public byte[] Name() {return name;} private final byte[] name; // EX: Earth
|
||||
public byte[] Descrip() {return descrip;} private final byte[] descrip; // EX: Third planet from the Sun
|
||||
public byte[] Img() {return img;} private final byte[] img; // EX: Earth.png
|
||||
}
|
||||
@@ -25,7 +25,7 @@ class Db_rdr_utl {
|
||||
}
|
||||
public static Mem_qry_set Load_as_qry_set(Db_conn conn, Dbmeta_fld_list fld_list, String sql) {
|
||||
Mem_qry_set qry_set = new Mem_qry_set();
|
||||
DataRdr rdr = conn.Exec_sql_as_rdr(sql);
|
||||
DataRdr rdr = conn.Exec_sql_as_old_rdr(sql);
|
||||
try {
|
||||
int fld_count = rdr.FieldCount();
|
||||
while (rdr.MoveNextPeer()) {
|
||||
@@ -42,7 +42,7 @@ class Db_rdr_utl {
|
||||
}
|
||||
public static Object[][] Load(Db_conn conn, String sql) {
|
||||
List_adp list = List_adp_.new_();
|
||||
DataRdr rdr = conn.Exec_sql_as_rdr(sql);
|
||||
DataRdr rdr = conn.Exec_sql_as_old_rdr(sql);
|
||||
try {
|
||||
int fld_count = rdr.FieldCount();
|
||||
while (rdr.MoveNextPeer()) {
|
||||
|
||||
@@ -26,7 +26,7 @@ class Xowd_cat_core_tbl__in_wkr extends Db_in_wkr__base {
|
||||
public void Init(Ordered_hash hash) {this.hash = hash;}
|
||||
@Override protected Db_qry Make_qry(int bgn, int end) {
|
||||
Object[] part_ary = In_ary(end - bgn);
|
||||
return Db_qry_.select_cols_(tbl_name, Db_crt_.in_(fld_cat_id, part_ary), flds.To_str_ary());
|
||||
return Db_qry_.select_cols_(tbl_name, Db_crt_.New_in(fld_cat_id, part_ary), flds.To_str_ary());
|
||||
}
|
||||
@Override protected void Fill_stmt(Db_stmt stmt, int bgn, int end) {
|
||||
for (int i = bgn; i < end; i++) {
|
||||
|
||||
@@ -54,11 +54,11 @@ public class Xowd_cat_link_tbl implements Rls_able {
|
||||
public int Select_by_type(List_adp list, int cat_page_id, byte arg_tid, byte[] arg_sortkey, boolean arg_is_from, int limit) {
|
||||
String arg_sortkey_str = arg_sortkey == null ? "" : String_.new_u8(arg_sortkey);
|
||||
gplx.core.criterias.Criteria comp_crt = !arg_is_from
|
||||
? Db_crt_.mte_(fld_sortkey, arg_sortkey_str) // from: sortkey >= 'val'
|
||||
: Db_crt_.lte_(fld_sortkey, arg_sortkey_str); // until: sortkey <= 'val'
|
||||
? Db_crt_.New_mte(fld_sortkey, arg_sortkey_str) // from: sortkey >= 'val'
|
||||
: Db_crt_.New_lte(fld_sortkey, arg_sortkey_str); // until: sortkey <= 'val'
|
||||
Db_qry__select_cmd qry = Db_qry_.select_().Cols_(fld_from, fld_sortkey).From_(tbl_name)
|
||||
.Where_(gplx.core.criterias.Criteria_.And_many(Db_crt_.eq_(fld_to_id, -1), Db_crt_.eq_(fld_type_id, arg_tid), comp_crt))
|
||||
.OrderBy_(fld_sortkey, !arg_is_from)
|
||||
.Where_(gplx.core.criterias.Criteria_.And_many(Db_crt_.New_eq(fld_to_id, -1), Db_crt_.New_eq(fld_type_id, arg_tid), comp_crt))
|
||||
.Order_(fld_sortkey, !arg_is_from)
|
||||
.Limit_(limit + 1); // + 1 to get last_plus_one for next page / previous page
|
||||
Db_rdr rdr = conn.Stmt_new(qry).Crt_int(fld_to_id, cat_page_id).Crt_byte(fld_type_id, arg_tid).Crt_str(fld_sortkey, arg_sortkey_str).Exec_select__rls_auto();
|
||||
int count = 0;
|
||||
|
||||
@@ -31,6 +31,7 @@ public class Xowd_page_tbl implements Rls_able {
|
||||
public String Fld_page_title() {return fld_title;}
|
||||
public String Fld_page_len() {return fld_len;}
|
||||
public String Fld_html_db_id() {return fld_html_db_id;}
|
||||
public String Fld_is_redirect() {return fld_is_redirect;}
|
||||
public String Fld_redirect_id() {return fld_redirect_id;}
|
||||
public String[] Flds_select_idx() {return flds_select_idx;}
|
||||
public String[] Flds_select_all() {return flds_select_all;}
|
||||
@@ -111,7 +112,7 @@ public class Xowd_page_tbl implements Rls_able {
|
||||
return false;
|
||||
}
|
||||
public Db_rdr Select_all() {
|
||||
Db_qry__select_cmd qry = Db_qry__select_cmd.new_().From_(tbl_name).Cols_(fld_id, fld_title).OrderBy_asc_(fld_id);
|
||||
Db_qry__select_cmd qry = new Db_qry__select_cmd().From_(tbl_name).Cols_(fld_id, fld_title).Order_asc_(fld_id);
|
||||
return conn.Stmt_new(qry).Exec_select__rls_auto();
|
||||
}
|
||||
public int Select_id(int ns_id, byte[] ttl) {
|
||||
@@ -167,7 +168,7 @@ public class Xowd_page_tbl implements Rls_able {
|
||||
}
|
||||
public void Select_by_search(Cancelable cancelable, List_adp rv, byte[] search, int results_max) {
|
||||
if (Bry_.Len_eq_0(search)) return; // do not allow empty search
|
||||
Criteria crt = Criteria_.And_many(Db_crt_.eq_(fld_ns, Xow_ns_.Tid__main), Db_crt_.like_(fld_title, ""));
|
||||
Criteria crt = Criteria_.And_many(Db_crt_.New_eq(fld_ns, Xow_ns_.Tid__main), Db_crt_.New_like(fld_title, ""));
|
||||
Db_qry__select_cmd qry = Db_qry_.select_().From_(tbl_name).Cols_(fld_id, fld_len, fld_ns, fld_title).Where_(crt); // NOTE: use fields from main index only
|
||||
search = Bry_.Replace(search, Byte_ascii.Star, Byte_ascii.Percent);
|
||||
Db_rdr rdr = conn.Stmt_new(qry).Clear().Crt_int(fld_ns, Xow_ns_.Tid__main).Val_bry_as_str(fld_title, search).Exec_select__rls_auto();
|
||||
@@ -207,16 +208,16 @@ public class Xowd_page_tbl implements Rls_able {
|
||||
}
|
||||
private Db_rdr Load_ttls_starting_with_rdr(int ns_id, byte[] ttl_frag, boolean include_redirects, int max_results, int min_page_len, int browse_len, boolean fwd, boolean search_suggest) {
|
||||
String ttl_frag_str = String_.new_u8(ttl_frag);
|
||||
Criteria crt_ttl = fwd ? Db_crt_.mte_(fld_title, ttl_frag_str) : Db_crt_.lt_(fld_title, ttl_frag_str);
|
||||
Criteria crt = Criteria_.And_many(Db_crt_.eq_(fld_ns, ns_id), crt_ttl, Db_crt_.mte_(fld_len, min_page_len));
|
||||
Criteria crt_ttl = fwd ? Db_crt_.New_mte(fld_title, ttl_frag_str) : Db_crt_.New_lt(fld_title, ttl_frag_str);
|
||||
Criteria crt = Criteria_.And_many(Db_crt_.New_eq(fld_ns, ns_id), crt_ttl, Db_crt_.New_mte(fld_len, min_page_len));
|
||||
if (!include_redirects)
|
||||
crt = Criteria_.And(crt, Db_crt_.eq_(fld_is_redirect, Byte_.Zero));
|
||||
crt = Criteria_.And(crt, Db_crt_.New_eq(fld_is_redirect, Byte_.Zero));
|
||||
String[] cols = search_suggest
|
||||
? flds_select_idx
|
||||
: flds_select_all
|
||||
;
|
||||
int limit = fwd ? max_results + 1 : max_results; // + 1 to get next item
|
||||
Db_qry__select_cmd qry = Db_qry_.select_cols_(tbl_name, crt, cols).Limit_(limit).OrderBy_(fld_title, fwd);
|
||||
Db_qry__select_cmd qry = Db_qry_.select_cols_(tbl_name, crt, cols).Limit_(limit).Order_(fld_title, fwd);
|
||||
Db_stmt stmt = conn.Stmt_new(qry).Crt_int(fld_ns, ns_id).Crt_str(fld_title, ttl_frag_str).Crt_int(fld_len, min_page_len);
|
||||
if (!include_redirects)
|
||||
stmt.Crt_bool_as_byte(fld_is_redirect, include_redirects);
|
||||
|
||||
@@ -28,7 +28,7 @@ class Xowd_page_tbl__ttl_ns extends Xowd_page_tbl__in_wkr__base {
|
||||
Criteria[] crt_ary = new Criteria[len];
|
||||
String fld_ns = tbl.Fld_page_ns(); String fld_ttl = tbl.Fld_page_title();
|
||||
for (int i = 0; i < len; i++)
|
||||
crt_ary[i] = Criteria_.And(Db_crt_.eq_(fld_ns, 0), Db_crt_.eq_(fld_ttl, Bry_.Empty));
|
||||
crt_ary[i] = Criteria_.And(Db_crt_.New_eq(fld_ns, 0), Db_crt_.New_eq(fld_ttl, Bry_.Empty));
|
||||
return Criteria_.Or_many(crt_ary);
|
||||
}
|
||||
@Override protected void Fill_stmt(Db_stmt stmt, int bgn, int end) {
|
||||
@@ -55,7 +55,7 @@ class Xowd_page_tbl__ttl extends Xowd_page_tbl__in_wkr__base {
|
||||
Criteria[] crt_ary = new Criteria[len];
|
||||
String fld_ns = tbl.Fld_page_ns(); String fld_ttl = tbl.Fld_page_title();
|
||||
for (int i = 0; i < len; i++)
|
||||
crt_ary[i] = Criteria_.And(Db_crt_.eq_(fld_ns, in_ns), Db_crt_.eq_(fld_ttl, Bry_.Empty));
|
||||
crt_ary[i] = Criteria_.And(Db_crt_.New_eq(fld_ns, in_ns), Db_crt_.New_eq(fld_ttl, Bry_.Empty));
|
||||
return Criteria_.Or_many(crt_ary);
|
||||
}
|
||||
@Override protected void Fill_stmt(Db_stmt stmt, int bgn, int end) {
|
||||
@@ -73,7 +73,7 @@ class Xowd_page_tbl__id extends Xowd_page_tbl__in_wkr__base {
|
||||
public void Init(List_adp list, Ordered_hash hash) {this.list = list; this.hash = hash; this.Fill_idx_fields_only_(true);}
|
||||
@Override protected boolean Show_progress() {return true;}
|
||||
@Override protected Criteria In_filter(Object[] part_ary) {
|
||||
return Db_crt_.in_(this.In_fld_name(), part_ary);
|
||||
return Db_crt_.New_in(this.In_fld_name(), part_ary);
|
||||
}
|
||||
@Override protected void Fill_stmt(Db_stmt stmt, int bgn, int end) {
|
||||
for (int i = bgn; i < end; i++) {
|
||||
|
||||
@@ -21,7 +21,7 @@ import gplx.dbs.*; import gplx.dbs.utls.*;
|
||||
public class Xowd_search_link_tbl {
|
||||
private final String tbl_name; private final Dbmeta_fld_list flds = Dbmeta_fld_list.new_();
|
||||
private final String fld_word_id, fld_page_id;
|
||||
private final Db_conn conn; private Db_stmt stmt_insert; private final Xowd_search_page_tbl__in_wkr in_wkr = new Xowd_search_page_tbl__in_wkr();
|
||||
public final Db_conn conn; private Db_stmt stmt_insert; private final Xowd_search_page_tbl__in_wkr in_wkr = new Xowd_search_page_tbl__in_wkr();
|
||||
public Xowd_search_link_tbl(Db_conn conn, boolean schema_is_1) {
|
||||
this.conn = conn;
|
||||
String fld_prefix = "";
|
||||
@@ -56,7 +56,7 @@ class Xowd_search_page_tbl__in_wkr extends Db_in_wkr__base {
|
||||
public void Init(List_adp words, List_adp pages) {this.words = words; this.pages = pages;}
|
||||
@Override protected Db_qry Make_qry(int bgn, int end) {
|
||||
Object[] part_ary = In_ary(end - bgn);
|
||||
return Db_qry_.select_cols_(tbl_name, Db_crt_.in_(fld_word_id, part_ary), flds.To_str_ary());
|
||||
return Db_qry_.select_cols_(tbl_name, Db_crt_.New_in(fld_word_id, part_ary), flds.To_str_ary());
|
||||
}
|
||||
@Override protected void Fill_stmt(Db_stmt stmt, int bgn, int end) {
|
||||
for (int i = bgn; i < end; i++) {
|
||||
|
||||
@@ -18,7 +18,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
package gplx.xowa.wikis.data.tbls; import gplx.*; import gplx.xowa.*; import gplx.xowa.wikis.*; import gplx.xowa.wikis.data.*;
|
||||
import gplx.dbs.*; import gplx.dbs.engines.sqlite.*;
|
||||
public class Xowd_search_temp_tbl {
|
||||
private final String tbl_name = "search_temp"; private final Dbmeta_fld_list flds = Dbmeta_fld_list.new_();
|
||||
private final Dbmeta_fld_list flds = Dbmeta_fld_list.new_();
|
||||
private final String fld_page_id, fld_word_text;
|
||||
private final Db_conn conn; private Db_stmt stmt_insert;
|
||||
private final String sql_create_word, sql_create_link;
|
||||
@@ -26,10 +26,12 @@ public class Xowd_search_temp_tbl {
|
||||
this.conn = conn;
|
||||
if (schema_is_1) {sql_create_word = Sql_create_word_v1; sql_create_link = Sql_create_link_v1;}
|
||||
else {sql_create_word = Sql_create_word_v2; sql_create_link = Sql_create_link_v2;}
|
||||
// flds.Add_int_dflt("word_id", -1);
|
||||
flds.Add_int_pkey_autonum("word_id");
|
||||
fld_page_id = flds.Add_int("page_id");
|
||||
fld_word_text = flds.Add_str("word_text", 255);
|
||||
}
|
||||
public String Tbl_name() {return tbl_name;} private final String tbl_name = "search_temp";
|
||||
public void Create_tbl() {conn.Ddl_create_tbl(Dbmeta_tbl_itm.New(tbl_name, flds));}
|
||||
public void Insert_bgn() {conn.Txn_bgn("schema__search_temp__insert"); stmt_insert = conn.Stmt_insert(tbl_name, flds);}
|
||||
public void Insert_end() {conn.Txn_end(); stmt_insert = Db_stmt_.Rls(stmt_insert);}
|
||||
@@ -40,7 +42,9 @@ public class Xowd_search_temp_tbl {
|
||||
}
|
||||
public void Make_data(Gfo_usr_dlg usr_dlg, Xowd_search_link_tbl search_link_tbl, Xowd_search_word_tbl search_word_tbl) {
|
||||
conn.Ddl_create_idx(usr_dlg, Dbmeta_idx_itm.new_unique_by_tbl(tbl_name, "main", fld_word_text, fld_page_id));
|
||||
conn.Exec_delete_all(search_word_tbl.Tbl_name());
|
||||
conn.Exec_sql_plog_txn("search_temp.create_word", sql_create_word);
|
||||
conn.Exec_delete_all(search_link_tbl.Tbl_name());
|
||||
conn.Exec_sql_plog_txn("search_temp.create_link", sql_create_link);
|
||||
Create_idx(usr_dlg, search_link_tbl, search_word_tbl);
|
||||
conn.Env_vacuum();
|
||||
@@ -55,6 +59,23 @@ public class Xowd_search_temp_tbl {
|
||||
search_link_tbl.Create_idx_normal();;
|
||||
}
|
||||
}
|
||||
public void Update_word_id(Db_conn cur_conn, Io_url prv_url) {
|
||||
String sql = String_.Concat_lines_nl_skip_last
|
||||
( "REPLACE INTO search_temp (word_id, page_id, word_text)"
|
||||
, "SELECT Coalesce(prv.word_id, cur.word_id), cur.page_id, cur.word_text"
|
||||
, "FROM search_temp cur"
|
||||
, " LEFT JOIN <attach_db>search_word prv ON cur.word_text = prv.word_text"
|
||||
);
|
||||
Db_attach_cmd.new_(cur_conn, "prv_db", prv_url).Add_fmt("updating_word_ids", sql).Exec();
|
||||
Db_stmt update_stmt = cur_conn.Stmt_update(tbl_name, String_.Ary(fld_word_text), fld_page_id);
|
||||
Db_rdr rdr = cur_conn.Stmt_select(tbl_name, flds, String_.Ary(fld_page_id)).Crt_int(fld_page_id, -1).Exec_select__rls_auto();
|
||||
int nxt_page_id = 1000;
|
||||
try {
|
||||
while (rdr.Move_next()) {
|
||||
update_stmt.Crt_int(fld_page_id, ++nxt_page_id).Exec_update();
|
||||
}
|
||||
} finally {rdr.Rls();}
|
||||
}
|
||||
private static final String Sql_create_word_v1 = String_.Concat_lines_nl
|
||||
( "INSERT INTO search_title_word (stw_word_id, stw_word)"
|
||||
, "SELECT word_id"
|
||||
|
||||
@@ -20,7 +20,7 @@ import gplx.core.primitives.*; import gplx.dbs.*; import gplx.dbs.cfgs.*; import
|
||||
public class Xowd_search_word_tbl implements Rls_able {
|
||||
private final String tbl_name; private final Dbmeta_fld_list flds = Dbmeta_fld_list.new_();
|
||||
private final String fld_id, fld_text; private String fld_page_count; private boolean page_count_exists;
|
||||
private final Db_conn conn; private Db_stmt stmt_insert, stmt_select_by, stmt_select_in;
|
||||
public final Db_conn conn; private Db_stmt stmt_insert, stmt_select_by, stmt_select_in;
|
||||
public Xowd_search_word_tbl(Db_conn conn, boolean schema_is_1, boolean page_count_exists) {
|
||||
this.conn = conn; this.page_count_exists = page_count_exists;
|
||||
String fld_prefix = "", fld_text_name = "word_text";
|
||||
@@ -31,6 +31,11 @@ public class Xowd_search_word_tbl implements Rls_able {
|
||||
this.fld_page_count = page_count_exists ? flds.Add_int_dflt("word_page_count", 0) : Dbmeta_fld_itm.Key_null;
|
||||
conn.Rls_reg(this);
|
||||
}
|
||||
public String Tbl_name() {return tbl_name;}
|
||||
public String Fld_id() {return fld_id;}
|
||||
public String Fld_text() {return fld_text;}
|
||||
public String Fld_page_count() {return fld_page_count;}
|
||||
public String Fld_page_score_max() {return Dbmeta_fld_itm.Key_null;}
|
||||
public void Create_tbl() {conn.Ddl_create_tbl(Dbmeta_tbl_itm.New(tbl_name, flds));}
|
||||
public void Create_idx() {conn.Ddl_create_idx(Xoa_app_.Usr_dlg(), Dbmeta_idx_itm.new_unique_by_tbl(tbl_name, "main", fld_text, fld_id, fld_page_count));}
|
||||
public void Insert_bgn() {conn.Txn_bgn("schema__search_word__insert"); stmt_insert = conn.Stmt_insert(tbl_name, flds);}
|
||||
@@ -52,7 +57,7 @@ public class Xowd_search_word_tbl implements Rls_able {
|
||||
}
|
||||
public Xowd_search_word_row[] Select_in(Cancelable cxl, byte[] word) {
|
||||
if (stmt_select_in == null) {
|
||||
Db_qry__select_cmd qry = Db_qry_.select_().From_(tbl_name).OrderBy_(fld_page_count, Bool_.N).Where_(Db_crt_.like_(fld_text, "")); // order by highest page count to look at most common words
|
||||
Db_qry__select_cmd qry = Db_qry_.select_().From_(tbl_name).Order_(fld_page_count, Bool_.N).Where_(Db_crt_.New_like(fld_text, "")); // order by highest page count to look at most common words
|
||||
stmt_select_in = conn.Stmt_new(qry);
|
||||
}
|
||||
List_adp list = List_adp_.new_();
|
||||
@@ -74,10 +79,10 @@ public class Xowd_search_word_tbl implements Rls_able {
|
||||
gplx.core.criterias.Criteria crt = null;
|
||||
if (Bry_.Has(search, Byte_ascii.Star)) {
|
||||
search = Bry_.Replace(search, Byte_ascii.Star, Byte_ascii.Percent);
|
||||
crt = Db_crt_.like_ (fld_text, String_.new_u8(search));
|
||||
crt = Db_crt_.New_like (fld_text, String_.new_u8(search));
|
||||
}
|
||||
else
|
||||
crt = Db_crt_.eq_ (fld_text, String_.new_u8(search));
|
||||
crt = Db_crt_.New_eq (fld_text, String_.new_u8(search));
|
||||
Db_qry__select_cmd qry = Db_qry_.select_().Cols_(fld_id).From_(tbl_name).Where_(crt);
|
||||
|
||||
List_adp words = List_adp_.new_();
|
||||
|
||||
@@ -51,7 +51,7 @@ class Xodb_upgrade_mgr {
|
||||
// }
|
||||
// }
|
||||
// private static void Fix_category_version(Db_conn p, Xodb_mgr_sql db_mgr) {
|
||||
// Db_qry qry = Db_qry_.select_().From_(Xodb_categorylinks_tbl.Tbl_name).Cols_(Xodb_categorylinks_tbl.Fld_cl_type_id).Where_(Db_crt_.eq_(Xodb_categorylinks_tbl.Fld_cl_type_id, ));
|
||||
// Db_qry qry = Db_qry_.select_().From_(Xodb_categorylinks_tbl.Tbl_name).Cols_(Xodb_categorylinks_tbl.Fld_cl_type_id).Where_(Db_crt_.New_eq(Xodb_categorylinks_tbl.Fld_cl_type_id, ));
|
||||
// Db_stmt stmt = Db_stmt_.Null;
|
||||
// DataRdr rdr = DataRdr_.Null;
|
||||
// int types = 0;
|
||||
|
||||
@@ -27,7 +27,7 @@ public class Xopg_page_heading implements Bfr_arg {
|
||||
}
|
||||
public void Bfr_arg__add(Bry_bfr bfr) {
|
||||
if (html_data.Xtn_pgbnr() != null) return; // pgbnr exists; don't add title
|
||||
fmtr.Bld_bfr_many(bfr, page_ttl.Page_txt());
|
||||
fmtr.Bld_many(bfr, page_ttl.Page_txt());
|
||||
}
|
||||
private final Bry_fmt fmtr = Bry_fmt.New(Bry_.New_u8_nl_apos("<h1 id='firstHeading' class='firstHeading'><span>~{page_title}</span></h1>"), "page_title");
|
||||
}
|
||||
|
||||
@@ -22,7 +22,7 @@ public class Pgbnr_icon implements Mustache_doc_itm {
|
||||
private final byte[] name, title, href, html;
|
||||
public Pgbnr_icon(Bry_bfr tmp_bfr, byte[] name, byte[] title, byte[] href) {
|
||||
this.name = name; this.title = title; this.href = href;
|
||||
fmt.Bld_bfr_many(tmp_bfr, name, title);
|
||||
fmt.Bld_many(tmp_bfr, name, title);
|
||||
this.html = tmp_bfr.To_bry_and_clear();
|
||||
}
|
||||
public byte[] Get_prop(String key) {
|
||||
|
||||
Reference in New Issue
Block a user