diff --git a/100_core/src/gplx/core/envs/Runtime_.java b/100_core/src/gplx/core/envs/Runtime_.java
index 34d397c12..98d4667df 100644
--- a/100_core/src/gplx/core/envs/Runtime_.java
+++ b/100_core/src/gplx/core/envs/Runtime_.java
@@ -22,4 +22,12 @@ public class Runtime_ {
public static long Memory_max() {return Runtime.getRuntime().maxMemory();}
public static long Memory_total() {return Runtime.getRuntime().totalMemory();}
public static long Memory_free() {return Runtime.getRuntime().freeMemory();}
+
+ public static void Exec(String v) {
+ try {
+ Runtime.getRuntime().exec(v);
+ } catch (Exception e) {
+ Gfo_usr_dlg_.Instance.Log_many("", "", "runtime exec failed; err=~{0}", Err_.Message_gplx_log(e));
+ }
+ }
}
\ No newline at end of file
diff --git a/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_item.java b/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_item.java
index af5922c28..cf6fee04e 100644
--- a/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_item.java
+++ b/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_item.java
@@ -16,7 +16,7 @@ You should have received a copy of the GNU Affero General Public License
along with this program. If not, see .
*/
package gplx.xowa.addons.apps.updates.apps; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.apps.*; import gplx.xowa.addons.apps.updates.*;
-class Xoa_manifest_item {
+public class Xoa_manifest_item {
public Xoa_manifest_item(Io_url src, Io_url trg) {
this.src = src;
this.trg = trg;
diff --git a/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_list.java b/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_list.java
index 9847d5f33..aeef06ff3 100644
--- a/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_list.java
+++ b/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_list.java
@@ -16,7 +16,7 @@ You should have received a copy of the GNU Affero General Public License
along with this program. If not, see .
*/
package gplx.xowa.addons.apps.updates.apps; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.apps.*; import gplx.xowa.addons.apps.updates.*;
-class Xoa_manifest_list {
+public class Xoa_manifest_list {
private final Ordered_hash hash = Ordered_hash_.New();
public int Len() {return hash.Len();}
public Xoa_manifest_item Get_at(int i) {return (Xoa_manifest_item)hash.Get_at(i);}
diff --git a/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_view.java b/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_view.java
index eac89ca9c..3ab43fc0c 100644
--- a/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_view.java
+++ b/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_view.java
@@ -16,17 +16,99 @@ You should have received a copy of the GNU Affero General Public License
along with this program. If not, see .
*/
package gplx.xowa.addons.apps.updates.apps; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.apps.*; import gplx.xowa.addons.apps.updates.*;
-public class Xoa_manifest_view {
+import gplx.core.envs.*;
+import java.awt.*;
+import java.awt.event.MouseAdapter;
+import java.awt.event.MouseEvent;
+import java.io.IOException;
+import java.net.*;
+import javax.swing.*;
+import javax.swing.border.Border;
+public class Xoa_manifest_view extends JFrame implements Gfo_invk {
private final Xoa_manifest_wkr wkr;
- public Xoa_manifest_view(String manifest_url) {
- this.wkr = new Xoa_manifest_wkr(this);
+ private String run_xowa_cmd;
+ public Xoa_manifest_view(Io_url manifest_url) {
+ super("XOWA Application Update");
+ // init window
+ this.setTitle("XOWA Application Update");
+ try {
+ UIManager.setLookAndFeel(
+ UIManager.getSystemLookAndFeelClassName());
+ }
+ catch (Exception e) {System.out.println(e.getMessage());}
+ this.setSize(700, 580);
+ this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
+ this.setLocationRelativeTo(null);
+ this.setBackground(Color.WHITE);
+
+ // init panel
+ JPanel main_panel = new JPanel();
+ main_panel.setSize(700, 580);
+ this.setContentPane(main_panel);
+ New_text_area(main_panel);
+ run_xowa_lbl = New_link_lbl(this, main_panel, Invk__run_xowa, "Run XOWA");
+ this.setVisible(true);
+ this.wkr = new Xoa_manifest_wkr(this);
wkr.Init(manifest_url);
}
- public void Append(String s) {
- }
+ private JTextArea text_area;
+ private JLabel run_xowa_lbl;
+ private JScrollPane New_text_area(JPanel owner) {
+ // init textarea
+ text_area = new JTextArea();
+ text_area.setForeground(Color.BLACK);
+ text_area.setBackground(Color.WHITE);
+ text_area.setMargin(new Insets(0, 0, 0,0));
+ text_area.setLineWrap(true);
+ text_area.setWrapStyleWord(true); // else text will wrap in middle of words
+ text_area.setCaretColor(Color.BLACK);
+ text_area.getCaret().setBlinkRate(0);
+
+ // init scrollpane
+ JScrollPane text_scroll_pane = new JScrollPane(text_area);
+ text_scroll_pane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED);
+ owner.add(text_scroll_pane, BorderLayout.CENTER);
+ text_scroll_pane.setPreferredSize(new Dimension(675, 500));
+ return text_scroll_pane;
+ }
+ private static JLabel New_link_lbl(Gfo_invk invk, JPanel owner, String invk_cmd, String text) {
+ JLabel rv = new JLabel();
+ rv.setText(text);
+ rv.setPreferredSize(new Dimension(80, 20));
+ owner.add(rv, BorderLayout.PAGE_END);
+ return rv;
+ }
+ public void Append(String s) {
+ text_area.setText(text_area.getText() + "> " + s + "\n");
+ }
+ public void Mark_done(String s) {
+ this.run_xowa_cmd = s;
+ run_xowa_lbl.setText("Run XOWA");
+ run_xowa_lbl.setCursor(new Cursor(Cursor.HAND_CURSOR));
+ run_xowa_lbl.addMouseListener(new Swing_mouse_adapter(Gfo_invk_cmd.New_by_key(this, Invk__run_xowa)));
+ }
+ public Object Invk(GfsCtx ctx, int ikey, String k, GfoMsg m) {
+ if (ctx.Match(k, Invk__run_xowa)) {
+ Runtime_.Exec(run_xowa_cmd);
+ System_.Exit();
+ }
+ else return Gfo_invk_.Rv_unhandled;
+ return this;
+ } private static final String Invk__run_xowa = "run_xowa";
- public static void Run(String manifest_url) {
- if (!gplx.core.envs.Op_sys.Cur().Tid_is_osx())
+ public static void Run() {
+ Io_url manifest_url = Env_.AppUrl().GenNewExt(".txt");
+ if (!Op_sys.Cur().Tid_is_osx())
new Xoa_manifest_view(manifest_url);
}
}
+class Swing_mouse_adapter extends MouseAdapter {
+ private final Gfo_invk_cmd cmd;
+ public Swing_mouse_adapter(Gfo_invk_cmd cmd) {this.cmd = cmd;}
+ @Override public void mouseClicked(MouseEvent ev) {
+ try {cmd.Exec();}
+ catch (Exception e) {
+ System.out.println(Err_.Message_gplx_full(e));
+ }
+ }
+}
diff --git a/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_wkr.java b/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_wkr.java
index c565ba497..6a427ac99 100644
--- a/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_wkr.java
+++ b/400_xowa/src/gplx/xowa/addons/apps/updates/apps/Xoa_manifest_wkr.java
@@ -16,24 +16,25 @@ You should have received a copy of the GNU Affero General Public License
along with this program. If not, see .
*/
package gplx.xowa.addons.apps.updates.apps; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.apps.*; import gplx.xowa.addons.apps.updates.*;
+import gplx.core.envs.*;
class Xoa_manifest_wkr {
private final Xoa_manifest_view view;
private final Xoa_manifest_list list = new Xoa_manifest_list();
private Io_url manifest_url;
- private byte[] run_xowa_cmd;
+ private String run_xowa_cmd;
public Xoa_manifest_wkr(Xoa_manifest_view view) {
this.view = view;
}
- public void Init(String manifest_url_str) {
+ public void Init(Io_url manifest_url) {
// load manifest
- view.Append("loading manifest from: " + manifest_url_str);
- this.manifest_url = Io_url_.new_any_(manifest_url_str);
+ this.manifest_url = manifest_url;
+ view.Append("loading manifest from: " + manifest_url.Raw());
byte[] src = Io_mgr.Instance.LoadFilBry(manifest_url);
// parse manifest
int nl_pos = Bry_find_.Find_fwd(src, Byte_ascii.Nl);
- if (nl_pos == Bry_find_.Not_found) throw Err_.new_wo_type("could not find nl in manifest", "manifest_url", manifest_url_str);
- this.run_xowa_cmd = Bry_.Mid(src, 0, nl_pos);
+ if (nl_pos == Bry_find_.Not_found) throw Err_.new_wo_type("could not find nl in manifest", "manifest_url", manifest_url.Raw());
+ this.run_xowa_cmd = String_.new_u8(src, 0, nl_pos);
list.Load(src, nl_pos + 1, src.length);
this.Wait();
@@ -53,12 +54,11 @@ class Xoa_manifest_wkr {
view.Append("waiting for XOWA to release file: " + topmost);
}
}
+ this.On_exit();
}
public void On_exit() {
Io_mgr.Instance.DeleteFil(manifest_url);
- if (run_xowa_cmd != null)
- // gplx.core.envs.Process_adp.run_wait_arg_;
- gplx.core.envs.System_.Exit();
+ view.Mark_done(run_xowa_cmd);
}
private boolean Copy_files() {
// loop list and copy items
@@ -69,9 +69,10 @@ class Xoa_manifest_wkr {
try {
Io_mgr.Instance.DeleteFil_args(item.Trg()).MissingFails_off().Exec();
Io_mgr.Instance.CopyFil(item.Src(), item.Trg(), true);
+ view.Append(String_.Format("copied file: src={0} trg={1}", item.Src().Raw(), item.Trg().Raw()));
}
catch (Exception exc) {
- view.Append(String_.Format("failed to copy file: src={0} trg ={1} err={2}", item.Src().Raw(), item.Trg().Raw(), Err_.Message_lang(exc)));
+ view.Append(String_.Format("failed to copy file: src={0} trg={1} err={2}", item.Src().Raw(), item.Trg().Raw(), Err_.Message_lang(exc)));
return false;
}
}
diff --git a/400_xowa/src/gplx/xowa/addons/apps/updates/js/Xojs_wkr__replace.java b/400_xowa/src/gplx/xowa/addons/apps/updates/js/Xojs_wkr__replace.java
index 39c5dd673..0b811b0d3 100644
--- a/400_xowa/src/gplx/xowa/addons/apps/updates/js/Xojs_wkr__replace.java
+++ b/400_xowa/src/gplx/xowa/addons/apps/updates/js/Xojs_wkr__replace.java
@@ -16,7 +16,7 @@ You should have received a copy of the GNU Affero General Public License
along with this program. If not, see .
*/
package gplx.xowa.addons.apps.updates.js; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.apps.*; import gplx.xowa.addons.apps.updates.*;
-import gplx.xowa.guis.cbks.*;
+import gplx.xowa.guis.cbks.*;
public class Xojs_wkr__replace extends Xojs_wkr__base {
private final Io_url src_dir, trg_dir;
private final Io_url[] src_fils;
@@ -26,20 +26,30 @@ public class Xojs_wkr__replace extends Xojs_wkr__base {
this.src_fils = Io_mgr.Instance.QueryDir_args(src_dir).Recur_().ExecAsUrlAry();
this.Prog_data_end_(src_fils.length);
}
+ public Keyval[] Failed() {return failed;} private Keyval[] failed = Keyval_.Ary_empty;
@Override protected void Exec_run() {
+ List_adp failed_list = List_adp_.New();
+
int len = src_fils.length;
for (int i = 0; i < len; i++) {
+ if (this.Prog_notify_and_chk_if_suspended(i, len)) return; // stop if canceled
+
Io_url src_fil = src_fils[i];
Io_url trg_fil = trg_dir.GenSubFil(src_fil.GenRelUrl_orEmpty(src_dir));
- // Io_url trg_fil_del = trg_fil.GenNewNameAndExt(trg_fil.NameAndExt() + ".del");
try {
-// Io_mgr.Instance.DeleteFil(trg_fil);
-// Io_mgr.Instance.MoveFil_args(src_fil, trg_fil, true).Exec();
-
- Io_mgr.Instance.CopyFil(src_fil, trg_fil, true);
+ Io_mgr.Instance.DeleteFil(trg_fil); // delete first; will fail if file is in use
+ Io_mgr.Instance.MoveFil_args(src_fil, trg_fil, true).Exec(); // replace with src file
} catch (Exception exc) {
- Tfds.Write(src_fil, Err_.Message_lang(exc));
+ Gfo_usr_dlg_.Instance.Log_many("failed to delete and move file; file=~{0} msg=~{1}", trg_fil.Raw(), Err_.Message_gplx_log(exc));
+ failed_list.Add(Keyval_.new_(src_fil.Raw(), trg_fil.Raw()));
+ try {
+ Io_mgr.Instance.CopyFil(src_fil, trg_fil, true); // try to copy file anyway
+ } catch (Exception exc2) {
+ Gfo_usr_dlg_.Instance.Log_many("failed to fopy file; file=~{0} msg=~{1}", trg_fil.Raw(), Err_.Message_gplx_log(exc2));
+ }
}
}
+
+ this.failed = (Keyval[])failed_list.To_ary_and_clear(Keyval.class);
}
}
diff --git a/400_xowa/src/gplx/xowa/addons/apps/updates/specials/Xoa_update_controller.java b/400_xowa/src/gplx/xowa/addons/apps/updates/specials/Xoa_update_controller.java
index 2213d07d0..0cebd6a54 100644
--- a/400_xowa/src/gplx/xowa/addons/apps/updates/specials/Xoa_update_controller.java
+++ b/400_xowa/src/gplx/xowa/addons/apps/updates/specials/Xoa_update_controller.java
@@ -18,11 +18,14 @@ along with this program. If not, see .
package gplx.xowa.addons.apps.updates.specials; import gplx.*; import gplx.xowa.*; import gplx.xowa.addons.*; import gplx.xowa.addons.apps.*; import gplx.xowa.addons.apps.updates.*;
import gplx.xowa.guis.cbks.*;
import gplx.core.gfobjs.*;
-import gplx.xowa.addons.apps.updates.dbs.*; import gplx.xowa.addons.apps.updates.js.*;
+import gplx.xowa.addons.apps.updates.dbs.*; import gplx.xowa.addons.apps.updates.js.*;
+import gplx.xowa.addons.apps.updates.apps.*;
class Xoa_update_controller implements Gfo_invk {
+ private Io_url app_root_dir, update_dir;
public void Update_app(Xoa_app app, String version_name) {
// get app_version from db
- Io_url update_dir = app.Fsys_mgr().Root_dir().GenSubDir_nest("user", "app", "update");
+ this.app_root_dir = app.Fsys_mgr().Root_dir();
+ this.update_dir = app_root_dir.GenSubDir_nest("user", "app", "update");
Io_url update_db_fil = update_dir.GenSubFil_nest("xoa_update.sqlite3");
Xoa_update_db_mgr db_mgr = new Xoa_update_db_mgr(update_db_fil);
Xoa_app_version_itm version_itm = db_mgr.Tbl__app_version().Select_by_version_or_null(version_name);
@@ -50,13 +53,39 @@ class Xoa_update_controller implements Gfo_invk {
Xojs_wkr__unzip unzip_wkr = (Xojs_wkr__unzip)m.ReadObj("v");
Io_url src = unzip_wkr.Trg();
Io_url trg = Io_url_.new_dir_("D:\\xowa_temp\\");
+
+ // copy update_jar
+ Io_url src_jar_fil = app_root_dir.GenSubFil_nest("bin", "any", "xowa", "addon", "app", "update", "xoa_update.jar");
+ Io_url trg_jar_fil = update_dir.GenSubFil_nest("xoa_update.jar");
+ Io_mgr.Instance.MoveFil_args(src_jar_fil, trg_jar_fil, true).MissingFails_off().Exec();
+
Xojs_wkr__replace replace_wkr = new Xojs_wkr__replace(unzip_wkr.Cbk_mgr(), unzip_wkr.Cbk_trg(), "xo.app_updater.download__prog", Gfo_invk_cmd.New_by_key(this, Invk__replace_done), src, trg);
replace_wkr.Exec_async("app_updater");
}
private void On_replace_done(GfoMsg m) {
Xojs_wkr__replace replace_wkr = (Xojs_wkr__replace)m.ReadObj("v");
+
+ // get failed
+ Xoa_manifest_list list = new Xoa_manifest_list();
+ Keyval[] failed_ary = replace_wkr.Failed();
+ int len = failed_ary.length;
+ for (int i = 0; i < len; i++) {
+ Keyval failed = failed_ary[i];
+ list.Add(Io_url_.new_fil_(failed.Key()), Io_url_.new_fil_(failed.Val_to_str_or_empty()));
+ }
+
+ // write failed
+ Bry_bfr bfr = Bry_bfr_.New();
+ Write_restart(bfr);
+ list.Save(bfr);
+ Io_mgr.Instance.SaveFilBfr(update_dir.GenSubFil("xoa_update.txt"), bfr);
+
replace_wkr.Cbk_mgr().Send_json(replace_wkr.Cbk_trg(), "xo.app_updater.download__prog", Gfobj_nde.New().Add_bool("done", true));
}
+ private void Write_restart(Bry_bfr bfr) {
+ String restart = String_.Format("D:\\xowa_temp\\xowa_64.exe\n");
+ bfr.Add_str_u8(restart);
+ }
public Object Invk(GfsCtx ctx, int ikey, String k, GfoMsg m) {
if (ctx.Match(k, Invk__download_done)) On_download_done(m);
else if (ctx.Match(k, Invk__unzip_done)) On_unzip_done(m);
diff --git a/400_xowa/src/gplx/xowa/htmls/hrefs/Xoh_href_parser.java b/400_xowa/src/gplx/xowa/htmls/hrefs/Xoh_href_parser.java
index 0d8586587..f74441f60 100644
--- a/400_xowa/src/gplx/xowa/htmls/hrefs/Xoh_href_parser.java
+++ b/400_xowa/src/gplx/xowa/htmls/hrefs/Xoh_href_parser.java
@@ -70,7 +70,7 @@ public class Xoh_href_parser {
}
}
rv.Page_bry_(tmp_page);
- if (tmp_page == null) { // handle xwiki lnke's to history page else null ref; EX:[http://ru.wikipedia.org/w/index.php?title&diff=19103464&oldid=18910980 ???????]; PAGE:ru.w:Project:??????_??_??????_??????/?????/?????????????/2009 DATE:2016-11-24
+ if (tmp_page == null) { // handle xwiki lnke's to history page else null ref; EX:[http://ru.wikipedia.org/w/index.php?title&diff=19103464&oldid=18910980 извещен]; PAGE:ru.w:Project:Заявки_на_снятие_флагов/Архив/Патрулирующие/2009 DATE:2016-11-24
rv.Tid_(Xoa_url_.Tid_inet);
}
break;