Skip to content

Commit

Permalink
1.rewrite sample and fix bug 2.compelete readme
Browse files Browse the repository at this point in the history
  • Loading branch information
JoeSteven committed Aug 21, 2018
1 parent 3bd58d9 commit edbdc82
Show file tree
Hide file tree
Showing 37 changed files with 204 additions and 51 deletions.
24 changes: 21 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,24 @@ XWebViewAssistant 提供给Android开发者更简单的WebView开发方式,基
- 支持`JSBridge` ,拦截URL或者`onJsPrompt`都的方式二选一(官方注解的方式本身不需要封装,如果使用注解的方式,关闭本库的`JSBridge`功能即可
- `JSBridge` 注册的Java方法支持权限管理,支持双向调用及回调

### Sample

- 可以通过输入框输入url进行加载


- add whitelist 和 authorize 这两个按钮分别可以将当前网站加入到白名单或者方法授权


- function: 后面有三个注册的Java方法,分别对应三种不同的权限,public都可以调用,private需要加入白名单可调用, authorized需要白名单或者授权可以调用。


- params:后面为三个方法的参数,json格式
- 最底部输入框为Java调用 js的sample

**该sample的前端调试页面放在asset目录中,你也可以在接入该库的时候使用这个页面进行本地调试,该页面由猴哥-[Jaeger](https://github.com/laobie) 友情赞助**

![sample](./sample.jpeg)

### 依赖


Expand Down Expand Up @@ -133,8 +151,8 @@ JSBridgeRegister register = JSBridgeRegister.create()
.register("toast", JSToast.class)// js 约定的方法名及真实方法
.register("login", JSLogin.class)
.register("user_info", JSUserInfo.class)
.whiteList("api.xwebview.com")// 设置域名白名单
.whiteList("api.xwebview.cn");
.whiteList("api.xwebview.com")// 设置域名白名单,支持两种方式,域名白名单,或者是正则匹配
.whiteListPattern(Pattern.compile("file:///android_asset.*"));
```

- `IMethodInitializer` 方法初始化器
Expand Down Expand Up @@ -163,7 +181,7 @@ public interface IJSBridgePromptParser {

// 满足协议则返回一个 JSMessage 对象,否则返回null
public class JSMessage {
public String url;// 调用该方法的网页url,可选
public String hostUrl;// 调用该方法的网页url,可选
public String callback;// 执行成功后需要回调的JS函数,可选
public String errorCallback;// 异常发生时回调的JS函数,可选
public String javaMethod;// 要调用的Java方法,必须
Expand Down
Binary file added sample.jpeg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
86 changes: 86 additions & 0 deletions sample/src/main/assets/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
<!DOCTYPE html>
<html>

<head>
<meta charset="utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<title>JSBridge Demo</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
<style>
button {
display: block;
padding: 10px 20px;
margin: 10px 20px;
background: rgb(39, 147, 248);
border-radius: 4px;
color: white;
outline: none;
border: none;
}

button:active {
background: rgb(7, 120, 224);
}

input {
display: block;
background: lightblue;
margin: 10px 0;
padding: 5px;
}

.input_wrapper {
margin: 10px 20px;
}
</style>
<script type="text/javascript">
function callJava(callback, error_callback) {
let fuction_name = document.getElementById('input_fuction').value
let params = document.getElementById('input_params').value

let url =
`Xwebview://call_java/?callback=${callback||'successCallback'}&error_callback=${error_callback||'errorCallback'}&func=${fuction_name}&params=${params||'{}'}`
console.log(url)
window.location = url
}

function successCallback() {
alert("success callback!");
}

function errorCallback() {
alert("error callback!");
}

function msg(msg) {
document.getElementById('input_msg').value = msg
}
</script>


</head>

<body>
<h3 style="text-align:center">JSBridge Demo</h3>

<div class="input_wrapper">
<div>input fuction name</div>
<input id="input_fuction" />
</div>

<div class="input_wrapper">
<div>input params</div>
<textarea id="input_params"></textarea>
</div>

<button onclick="callJava()">call java</button>
<!-- <button>toast_public</button> -->
<!-- <button>toast_authorize</button> -->

<div class="input_wrapper">
<div>receive msg</div>
<input id="input_msg" />
</div>
</body>

</html>
Original file line number Diff line number Diff line change
Expand Up @@ -15,12 +15,12 @@
*/
public class JSBridgeUrlParser implements IJSBridgeUrlParser{
@Override
public JSMessage parse(String url) {
if (!url.startsWith("Xwebview")) return null;
public JSMessage parse(String hostUrl, String url) {
if (!url.startsWith("xwebview")) return null;
Uri uri = Uri.parse(url);
try {
JSONObject params = new JSONObject(uri.getQueryParameter("params"));
return new JSMessage(url,
return new JSMessage(hostUrl,
uri.getQueryParameter("callback"),
uri.getQueryParameter("error_callback"),
uri.getQueryParameter("func"),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,6 @@ public void call(JSMessage message) {

@Override
public Permission permission() {
return Permission.PUBLIC;
return Permission.AUTHORIZED;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,13 +20,16 @@
import com.joey.xwebview.jsbridge.JSBridgeRegister;
import com.joey.xwebview.ui.IWebTitle;

import java.util.regex.Pattern;

public class SampleActivity extends AppCompatActivity implements IWebTitle {

private XWebView webView;
private EditText etUrl;
private EditText etJs;
private String authorized;
private boolean authorized;
private String whiteList;
private Pattern whiteListPattern;
private Button btnWhiteList;
private Button btnAuthorized;

Expand All @@ -43,39 +46,21 @@ protected void onCreate(Bundle savedInstanceState) {
.setCacheMode(WebSettings.LOAD_NO_CACHE)
.setProgressEnable(findViewById(R.id.progress_bar))
.setJSBridgeUrlEnabled(register(), new JSBridgeUrlParser())
.setJSBridgeAuthorizedChecker(this::isAuthorized);
.setJSBridgeAuthorizedChecker(this::isAuthorized)
.loadUrl("file:///android_asset/index.html");

findViewById(R.id.btn_load).setOnClickListener(v -> webView.loadUrl(etUrl.getText().toString()));
findViewById(R.id.btn_input).setOnClickListener(v-> webView.invokeJavaScript("msg", etJs.getText().toString()));
etUrl.setText("file:///android_asset/index.html");
findViewById(R.id.btn_load).setOnClickListener(this::load);
findViewById(R.id.btn_input).setOnClickListener(v->
webView.invokeJavaScript("msg", etJs.getText().toString()));
btnWhiteList = findViewById(R.id.btn_whitelist);
btnWhiteList.setOnClickListener(this::addWhiteList);
btnAuthorized = findViewById(R.id.btn_authorized);
btnAuthorized.setOnClickListener(this::authorized);
}

private void authorized(View view) {
if (TextUtils.isEmpty(authorized)) {
authorized = Uri.parse(etUrl.getText().toString()).getHost();
btnAuthorized.setText("UnAuthorize");
} else {
authorized = null;
btnAuthorized.setText("Authorize");
}
}

private void addWhiteList(View view) {
if (TextUtils.isEmpty(whiteList)) {
whiteList = Uri.parse(etUrl.getText().toString()).getHost();
btnWhiteList.setText("remove whitelist");
} else {
whiteList = null;
btnWhiteList.setText("add whitelist");
}
webView.setJSBridgeUrlEnabled(register(), new JSBridgeUrlParser());
}

private boolean isAuthorized(String javafunc, String url) {
return TextUtils.equals(authorized, Uri.parse(url).getHost());
return authorized;
}

private JSBridgeRegister register() {
Expand All @@ -89,6 +74,8 @@ private JSBridgeRegister register() {
});
if (!TextUtils.isEmpty(whiteList)) {
register.whiteList(whiteList);
} else if(whiteListPattern != null) {
register.whiteList(whiteListPattern);
}
return register;
}
Expand All @@ -108,4 +95,48 @@ public void onBackPressed() {
}
}

private void load(View view) {
whiteList = "ddd";
whiteListPattern = Pattern.compile(".*");
authorized = false;
addWhiteList(view);
authorized(view);
webView.loadUrl(etUrl.getText().toString());
}

private void authorized(View view) {
if (!authorized) {
authorized = true;
btnAuthorized.setText("UnAuthorize");
} else {
authorized = false;
btnAuthorized.setText("Authorize");
}
}

private void addWhiteList(View view) {
if (webView.webView().getUrl().contains("android_asset")) {
if (whiteListPattern == null) {
whiteList = null;
whiteListPattern = Pattern.compile("file:///android_asset.*");
btnWhiteList.setText("remove whitelist");
} else {
whiteListPattern = null;
btnWhiteList.setText("add whitelist");
}

}else {
if (TextUtils.isEmpty(whiteList)) {
whiteListPattern = null;
whiteList = Uri.parse(etUrl.getText().toString()).getHost();
btnWhiteList.setText("remove whitelist");
} else {
whiteList = null;
btnWhiteList.setText("add whitelist");
}
}

webView.setJSBridgeUrlEnabled(register(), new JSBridgeUrlParser())
.setJSBridgeAuthorizedChecker(this::isAuthorized);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,11 @@
android:layout_width="0dp"
android:layout_height="wrap_content" />
</LinearLayout>
<TextView
android:textIsSelectable="true"
android:text="function: toast_public toast_private toast_authorized \n\n params: {&quot;message&quot;:&quot;input your content here&quot;}"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<com.joey.xwebview.ui.XWebProgressBar
android:id="@+id/progress_bar"
android:visibility="gone"
Expand Down
File renamed without changes.
File renamed without changes.
File renamed without changes.
2 changes: 1 addition & 1 deletion settings.gradle
Original file line number Diff line number Diff line change
@@ -1 +1 @@
include ':app', ':xwebview'
include ':sample', ':xwebview'
Original file line number Diff line number Diff line change
Expand Up @@ -10,5 +10,5 @@
* date:2018/8/20
*/
public interface IJSBridgePromptParser {
JSMessage parse(String url, String message, String defaultValue, JsPromptResult result);
JSMessage parse(String hostUrl, String url, String message, String defaultValue, JsPromptResult result);
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,10 @@
import com.joey.xwebview.jsbridge.method.JSMessage;

/**
* Description: parse url
* Description: parse hostUrl
* author:Joey
* date:2018/8/20
*/
public interface IJSBridgeUrlParser {
JSMessage parse(String url);
JSMessage parse(String hostUrl, String url);
}
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ public void setAuthorizedChecker(IAuthorizedChecker checker) {
}

/**
* parse url to JSMessage
* parse hostUrl to JSMessage
*/
public void setUrlParser(IJSBridgeUrlParser parser){
if (promptParser != null){
Expand All @@ -53,7 +53,7 @@ public void setUrlParser(IJSBridgeUrlParser parser){
*/
public void setPromptParser(IJSBridgePromptParser parser){
if (urlParser != null){
XWebLog.error(new JSBridgeException("already choose intercept url to achieve JSBridge!"));
XWebLog.error(new JSBridgeException("already choose intercept hostUrl to achieve JSBridge!"));
return;
}
promptParser = parser;
Expand All @@ -74,9 +74,9 @@ public boolean isEnableJsForPrompt() {
public boolean checkJsBridge(String url, String message, String defaultValue, JsPromptResult result) {
JSMessage msg = null;
if (urlParser != null) {
msg = urlParser.parse(url);
msg = urlParser.parse(webView.webView().getUrl(), url);
} else if(promptParser != null) {
msg = promptParser.parse(url, message, defaultValue, result);
msg = promptParser.parse(webView.webView().getUrl(), url, message, defaultValue, result);
}
if (msg == null) return false;
invokeJavaMethod(msg);
Expand Down Expand Up @@ -121,21 +121,20 @@ private void invokeJavaMethod(JSMessage message) {
}
switch (method.permission()) {
case PRIVATE:
Uri uri = Uri.parse(message.url);
if (jsBridgeRegister.isInWhiteList(uri.getHost())) {
if (jsBridgeRegister.isInWhiteList(message.hostUrl)) {
method.invoke(message, webView);
} else {
XWebLog.error(new JSBridgeException("Java method:" + message.javaMethod +
" is private, host:" + uri.getHost() +
" is private, host:" + message.hostUrl +
" don't have permission, add host in white list to invoke private method!"));
}
break;
case AUTHORIZED:
if (authorizedChecker.isAuthorized(message.javaMethod, message.url)) {
if (authorizedChecker.isAuthorized(message.javaMethod, message.hostUrl) || jsBridgeRegister.isInWhiteList(message.hostUrl)) {
method.invoke(message, webView);
} else {
XWebLog.error(new JSBridgeException("Java method:" + message.javaMethod +
" permission is Authorized, url:" + message.url +
" permission is Authorized, hostUrl:" + message.hostUrl +
" don't have permission, check you AuthorizedChecker!"));
}
break;
Expand Down
Loading

0 comments on commit edbdc82

Please sign in to comment.