我如何将复杂的 javascript self 运行 函数注入 android 中的 webview?
How do i inject a complicated javascript self running function into a webview in android?
我正在尝试将 javascript 函数注入到我的网络视图 运行 服务器 url "www.myserver.com" 中。但是,我无法这样做。我尝试了几种方法但没有成功。我尝试设置 js 警报,在读取 js 文件时不会弹出。我不确定我做错了什么。到目前为止,这是我的代码:
我的 js 文件 "page.js":
(function() {
**alert("this is a test alert");**
if (window.page) {
return; // page has been loaded from somewhere, not to redefine it again
}
function Response(xhr) {
this.xhr = xhr;
this.status = xhr.status;
}
Response.prototype.getHeader = function(header) {
return this.xhr.getResponseHeader(header);
};
Response.prototype.getBody = function() {
return this.xhr.responseText;
};
function ajax(url, callback) {
//TODO support PUT method
var xhr = new XMLHttpRequest();
xhr.open("GET", url, true);
xhr.onerror = function(e) {
callback.onerror(e);
};
xhr.onreadystatechange = function(event) {
if (this.readyState != this.DONE || this.status == 0) {
return;
}
if (this.status != 200) {
var response = new Response(xhr);
callback.onfail(response);
return;
}
callback.onsuccess(this.responseText);
};
xhr.send();
};
var rpc = {
type: ["SMALL", "LARGE"],
exec: function(call, type) {// "call" conform to JSON-RPC 2.0
//TODO differentiate POST/GET based on rpc.type.SMALL/LARGE
var param = encodeURIComponent(JSON.stringify(call));
ajax("?_$b=" + param, {
onerror: function(e) {
//TODO use logging
alert("Error:"+e.toString());
},
onfail: function(response) {
//TODO use logging
alert("Failed:"+response.getBoby());
},
onsuccess: function(text) {
//TODO use logging
alert("page success:"+text);
},
});
}
};
var _$b = window.page = {
version: "0.1"
};
_$b.has = function(feature) {
// TODO support nested objects, e.g.: "cache.get"
return _$b[feature];
};
_$b.notify = function(id, data) {
// TODO invoke the function from native and send web event
// var event = document.createEvent('Event');
// event.initEvent(id, true, true);
// document.dispatchEvent(event);
alert("id:" + id + ";data:" + data);
};
_$b.navigate = function(url, title) {
rpc.exec(// JSON-RPC 2.0
{method: "navigate", params: {
"url": url,
"title": title
}}, rpc.type.SMALL);
};
_$b.cache = {};
_$b.cache.get = function(id) {
rpc.exec(
{method: "cache.get", params: {
"id": id,
}}, rpc.type.SMALL);
};
_$b.cache.put = function(id, obj, ts, ttl) {
rpc.exec(
{method: "cache.put", params: {
"id": id,
"obj": obj,
"ts": ts,
"ttl": ttl,
}}, rpc.type.LARGE);
};
_$b.cache.has = function(id) {
rpc.exec(
{method: "cache.has", params: {
"id": id,
}}, rpc.type.SMALL);
};
})();
这是我的网页视图代码:
@Override
public void onPageFinished(WebView view, String url) {
String javascript = "";
try{
AssetManager manager = view.getContext().getAssets();
InputStream is = manager.open("page.js");
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String line;
while (( line = br.readLine()) != null) {
javascript += line;
}
is.close();
}
catch(Exception e){}
view.loadUrl("javascript:" + javascript);
}
webview.setWebChromeClient(new WebChromeClient() {});
webview.loadUrl(url);
知道如何弹出警报吗?
注意:当我删除 js 中的所有功能并只保留警报时,警报有效,但在我重新添加必要的 js 功能后,警报不再有效。知道是什么阻止了它按预期注入 js 吗?
考虑这段代码。这是简单的 html & javascript 代码,模仿您的 page.js
<html>
<script type="text/javascript">
(function() { alert('inside function'); })
alert('ok');
</script>
</html>
执行这个,可以推导出函数内部的alert不会一开始就执行,除非你特意调用它
点击一下运行你的函数:(试试这个)
<html>
<input type="button" onclick="run()" value="Start" />
<script type="text/javascript">
var run = (function() { alert('inside function'); })
alert('ok');
</script>
</html>
到运行你的函数[Self 运行](试试这个)
<html>
<script type="text/javascript">
var run = (function() { alert('inside function'); })
alert('ok');
//you need to execute your function that you have named
run();
</script>
</html>
我正在尝试将 javascript 函数注入到我的网络视图 运行 服务器 url "www.myserver.com" 中。但是,我无法这样做。我尝试了几种方法但没有成功。我尝试设置 js 警报,在读取 js 文件时不会弹出。我不确定我做错了什么。到目前为止,这是我的代码: 我的 js 文件 "page.js":
(function() {
**alert("this is a test alert");**
if (window.page) {
return; // page has been loaded from somewhere, not to redefine it again
}
function Response(xhr) {
this.xhr = xhr;
this.status = xhr.status;
}
Response.prototype.getHeader = function(header) {
return this.xhr.getResponseHeader(header);
};
Response.prototype.getBody = function() {
return this.xhr.responseText;
};
function ajax(url, callback) {
//TODO support PUT method
var xhr = new XMLHttpRequest();
xhr.open("GET", url, true);
xhr.onerror = function(e) {
callback.onerror(e);
};
xhr.onreadystatechange = function(event) {
if (this.readyState != this.DONE || this.status == 0) {
return;
}
if (this.status != 200) {
var response = new Response(xhr);
callback.onfail(response);
return;
}
callback.onsuccess(this.responseText);
};
xhr.send();
};
var rpc = {
type: ["SMALL", "LARGE"],
exec: function(call, type) {// "call" conform to JSON-RPC 2.0
//TODO differentiate POST/GET based on rpc.type.SMALL/LARGE
var param = encodeURIComponent(JSON.stringify(call));
ajax("?_$b=" + param, {
onerror: function(e) {
//TODO use logging
alert("Error:"+e.toString());
},
onfail: function(response) {
//TODO use logging
alert("Failed:"+response.getBoby());
},
onsuccess: function(text) {
//TODO use logging
alert("page success:"+text);
},
});
}
};
var _$b = window.page = {
version: "0.1"
};
_$b.has = function(feature) {
// TODO support nested objects, e.g.: "cache.get"
return _$b[feature];
};
_$b.notify = function(id, data) {
// TODO invoke the function from native and send web event
// var event = document.createEvent('Event');
// event.initEvent(id, true, true);
// document.dispatchEvent(event);
alert("id:" + id + ";data:" + data);
};
_$b.navigate = function(url, title) {
rpc.exec(// JSON-RPC 2.0
{method: "navigate", params: {
"url": url,
"title": title
}}, rpc.type.SMALL);
};
_$b.cache = {};
_$b.cache.get = function(id) {
rpc.exec(
{method: "cache.get", params: {
"id": id,
}}, rpc.type.SMALL);
};
_$b.cache.put = function(id, obj, ts, ttl) {
rpc.exec(
{method: "cache.put", params: {
"id": id,
"obj": obj,
"ts": ts,
"ttl": ttl,
}}, rpc.type.LARGE);
};
_$b.cache.has = function(id) {
rpc.exec(
{method: "cache.has", params: {
"id": id,
}}, rpc.type.SMALL);
};
})();
这是我的网页视图代码:
@Override
public void onPageFinished(WebView view, String url) {
String javascript = "";
try{
AssetManager manager = view.getContext().getAssets();
InputStream is = manager.open("page.js");
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String line;
while (( line = br.readLine()) != null) {
javascript += line;
}
is.close();
}
catch(Exception e){}
view.loadUrl("javascript:" + javascript);
}
webview.setWebChromeClient(new WebChromeClient() {});
webview.loadUrl(url);
知道如何弹出警报吗? 注意:当我删除 js 中的所有功能并只保留警报时,警报有效,但在我重新添加必要的 js 功能后,警报不再有效。知道是什么阻止了它按预期注入 js 吗?
考虑这段代码。这是简单的 html & javascript 代码,模仿您的 page.js
<html>
<script type="text/javascript">
(function() { alert('inside function'); })
alert('ok');
</script>
</html>
执行这个,可以推导出函数内部的alert不会一开始就执行,除非你特意调用它
点击一下运行你的函数:(试试这个)
<html>
<input type="button" onclick="run()" value="Start" />
<script type="text/javascript">
var run = (function() { alert('inside function'); })
alert('ok');
</script>
</html>
到运行你的函数[Self 运行](试试这个)
<html>
<script type="text/javascript">
var run = (function() { alert('inside function'); })
alert('ok');
//you need to execute your function that you have named
run();
</script>
</html>