Loading core/java/android/webkit/BrowserFrame.java +42 −12 Original line number Diff line number Diff line Loading @@ -89,8 +89,19 @@ class BrowserFrame extends Handler { // Is this frame the main frame? private boolean mIsMainFrame; // Javascript interface object private class JSObject { Object object; boolean requireAnnotation; public JSObject(Object object, boolean requireAnnotation) { this.object = object; this.requireAnnotation = requireAnnotation; } } // Attached Javascript interfaces private Map<String, Object> mJavaScriptObjects; private Map<String, JSObject> mJavaScriptObjects; private Set<Object> mRemovedJavaScriptObjects; // Key store handler when Chromium HTTP stack is used. Loading Loading @@ -234,10 +245,8 @@ class BrowserFrame extends Handler { } sConfigCallback.addHandler(this); mJavaScriptObjects = javascriptInterfaces; if (mJavaScriptObjects == null) { mJavaScriptObjects = new HashMap<String, Object>(); } mJavaScriptObjects = new HashMap<String, JSObject>(); addJavaScriptObjects(javascriptInterfaces); mRemovedJavaScriptObjects = new HashSet<Object>(); mSettings = settings; Loading Loading @@ -590,15 +599,36 @@ class BrowserFrame extends Handler { Iterator<String> iter = mJavaScriptObjects.keySet().iterator(); while (iter.hasNext()) { String interfaceName = iter.next(); Object object = mJavaScriptObjects.get(interfaceName); if (object != null) { JSObject jsobject = mJavaScriptObjects.get(interfaceName); if (jsobject != null && jsobject.object != null) { nativeAddJavascriptInterface(nativeFramePointer, mJavaScriptObjects.get(interfaceName), interfaceName); jsobject.object, interfaceName, jsobject.requireAnnotation); } } mRemovedJavaScriptObjects.clear(); } /* * Add javascript objects to the internal list of objects. The default behavior * is to allow access to inherited methods (no annotation needed). This is only * used when js objects are passed through a constructor (via a hidden constructor). * * @TODO change the default behavior to be compatible with the public addjavascriptinterface */ private void addJavaScriptObjects(Map<String, Object> javascriptInterfaces) { // TODO in a separate CL provide logic to enable annotations for API level JB_MR1 and above. if (javascriptInterfaces == null) return; Iterator<String> iter = javascriptInterfaces.keySet().iterator(); while (iter.hasNext()) { String interfaceName = iter.next(); Object object = javascriptInterfaces.get(interfaceName); if (object != null) { mJavaScriptObjects.put(interfaceName, new JSObject(object, false)); } } } /** * This method is called by WebCore to check whether application * wants to hijack url loading Loading @@ -616,11 +646,11 @@ class BrowserFrame extends Handler { } } public void addJavascriptInterface(Object obj, String interfaceName) { public void addJavascriptInterface(Object obj, String interfaceName, boolean requireAnnotation) { assert obj != null; removeJavascriptInterface(interfaceName); mJavaScriptObjects.put(interfaceName, obj); mJavaScriptObjects.put(interfaceName, new JSObject(obj, requireAnnotation)); } public void removeJavascriptInterface(String interfaceName) { Loading Loading @@ -1245,7 +1275,7 @@ class BrowserFrame extends Handler { * Add a javascript interface to the main frame. */ private native void nativeAddJavascriptInterface(int nativeFramePointer, Object obj, String interfaceName); Object obj, String interfaceName, boolean requireAnnotation); public native void clearCache(); Loading core/java/android/webkit/JavascriptInterface.java 0 → 100644 +36 −0 Original line number Diff line number Diff line /* * Copyright (C) 2012 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package android.webkit; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; /** * Annotation that allows exposing methods to JavaScript. Starting from API level * {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1} and above, only methods explicitly * marked with this annotation are available to the Javascript code. See * {@link android.webkit.Webview#addJavaScriptInterface} for more information about it. * * @hide */ @SuppressWarnings("javadoc") @Retention(RetentionPolicy.RUNTIME) @Target({ElementType.METHOD}) public @interface JavascriptInterface { } No newline at end of file core/java/android/webkit/WebView.java +4 −0 Original line number Diff line number Diff line Loading @@ -26,6 +26,7 @@ import android.graphics.Picture; import android.graphics.Rect; import android.graphics.drawable.Drawable; import android.net.http.SslCertificate; import android.os.Build; import android.os.Bundle; import android.os.Looper; import android.os.Message; Loading Loading @@ -1507,6 +1508,9 @@ public class WebView extends AbsoluteLayout public void addJavascriptInterface(Object object, String name) { checkThread(); mProvider.addJavascriptInterface(object, name); // TODO in a separate CL provide logic to enable annotations for API level JB_MR1 and above. Don't forget to // update the doc, set a link to annotation and unhide the annotation. // also describe that fields of java objects are not accessible from JS. } /** Loading core/java/android/webkit/WebViewClassic.java +3 −0 Original line number Diff line number Diff line Loading @@ -4114,12 +4114,15 @@ public final class WebViewClassic implements WebViewProvider, WebViewProvider.Sc */ @Override public void addJavascriptInterface(Object object, String name) { if (object == null) { return; } WebViewCore.JSInterfaceData arg = new WebViewCore.JSInterfaceData(); // TODO in a separate CL provide logic to enable annotations for API level JB_MR1 and above. arg.mObject = object; arg.mInterfaceName = name; arg.mRequireAnnotation = false; mWebViewCore.sendMessage(EventHub.ADD_JS_INTERFACE, arg); } Loading core/java/android/webkit/WebViewCore.java +2 −1 Original line number Diff line number Diff line Loading @@ -824,6 +824,7 @@ public final class WebViewCore { static class JSInterfaceData { Object mObject; String mInterfaceName; boolean mRequireAnnotation; } static class JSKeyData { Loading Loading @@ -1489,7 +1490,7 @@ public final class WebViewCore { case ADD_JS_INTERFACE: JSInterfaceData jsData = (JSInterfaceData) msg.obj; mBrowserFrame.addJavascriptInterface(jsData.mObject, jsData.mInterfaceName); jsData.mInterfaceName, jsData.mRequireAnnotation); break; case REMOVE_JS_INTERFACE: Loading Loading
core/java/android/webkit/BrowserFrame.java +42 −12 Original line number Diff line number Diff line Loading @@ -89,8 +89,19 @@ class BrowserFrame extends Handler { // Is this frame the main frame? private boolean mIsMainFrame; // Javascript interface object private class JSObject { Object object; boolean requireAnnotation; public JSObject(Object object, boolean requireAnnotation) { this.object = object; this.requireAnnotation = requireAnnotation; } } // Attached Javascript interfaces private Map<String, Object> mJavaScriptObjects; private Map<String, JSObject> mJavaScriptObjects; private Set<Object> mRemovedJavaScriptObjects; // Key store handler when Chromium HTTP stack is used. Loading Loading @@ -234,10 +245,8 @@ class BrowserFrame extends Handler { } sConfigCallback.addHandler(this); mJavaScriptObjects = javascriptInterfaces; if (mJavaScriptObjects == null) { mJavaScriptObjects = new HashMap<String, Object>(); } mJavaScriptObjects = new HashMap<String, JSObject>(); addJavaScriptObjects(javascriptInterfaces); mRemovedJavaScriptObjects = new HashSet<Object>(); mSettings = settings; Loading Loading @@ -590,15 +599,36 @@ class BrowserFrame extends Handler { Iterator<String> iter = mJavaScriptObjects.keySet().iterator(); while (iter.hasNext()) { String interfaceName = iter.next(); Object object = mJavaScriptObjects.get(interfaceName); if (object != null) { JSObject jsobject = mJavaScriptObjects.get(interfaceName); if (jsobject != null && jsobject.object != null) { nativeAddJavascriptInterface(nativeFramePointer, mJavaScriptObjects.get(interfaceName), interfaceName); jsobject.object, interfaceName, jsobject.requireAnnotation); } } mRemovedJavaScriptObjects.clear(); } /* * Add javascript objects to the internal list of objects. The default behavior * is to allow access to inherited methods (no annotation needed). This is only * used when js objects are passed through a constructor (via a hidden constructor). * * @TODO change the default behavior to be compatible with the public addjavascriptinterface */ private void addJavaScriptObjects(Map<String, Object> javascriptInterfaces) { // TODO in a separate CL provide logic to enable annotations for API level JB_MR1 and above. if (javascriptInterfaces == null) return; Iterator<String> iter = javascriptInterfaces.keySet().iterator(); while (iter.hasNext()) { String interfaceName = iter.next(); Object object = javascriptInterfaces.get(interfaceName); if (object != null) { mJavaScriptObjects.put(interfaceName, new JSObject(object, false)); } } } /** * This method is called by WebCore to check whether application * wants to hijack url loading Loading @@ -616,11 +646,11 @@ class BrowserFrame extends Handler { } } public void addJavascriptInterface(Object obj, String interfaceName) { public void addJavascriptInterface(Object obj, String interfaceName, boolean requireAnnotation) { assert obj != null; removeJavascriptInterface(interfaceName); mJavaScriptObjects.put(interfaceName, obj); mJavaScriptObjects.put(interfaceName, new JSObject(obj, requireAnnotation)); } public void removeJavascriptInterface(String interfaceName) { Loading Loading @@ -1245,7 +1275,7 @@ class BrowserFrame extends Handler { * Add a javascript interface to the main frame. */ private native void nativeAddJavascriptInterface(int nativeFramePointer, Object obj, String interfaceName); Object obj, String interfaceName, boolean requireAnnotation); public native void clearCache(); Loading
core/java/android/webkit/JavascriptInterface.java 0 → 100644 +36 −0 Original line number Diff line number Diff line /* * Copyright (C) 2012 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package android.webkit; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; /** * Annotation that allows exposing methods to JavaScript. Starting from API level * {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1} and above, only methods explicitly * marked with this annotation are available to the Javascript code. See * {@link android.webkit.Webview#addJavaScriptInterface} for more information about it. * * @hide */ @SuppressWarnings("javadoc") @Retention(RetentionPolicy.RUNTIME) @Target({ElementType.METHOD}) public @interface JavascriptInterface { } No newline at end of file
core/java/android/webkit/WebView.java +4 −0 Original line number Diff line number Diff line Loading @@ -26,6 +26,7 @@ import android.graphics.Picture; import android.graphics.Rect; import android.graphics.drawable.Drawable; import android.net.http.SslCertificate; import android.os.Build; import android.os.Bundle; import android.os.Looper; import android.os.Message; Loading Loading @@ -1507,6 +1508,9 @@ public class WebView extends AbsoluteLayout public void addJavascriptInterface(Object object, String name) { checkThread(); mProvider.addJavascriptInterface(object, name); // TODO in a separate CL provide logic to enable annotations for API level JB_MR1 and above. Don't forget to // update the doc, set a link to annotation and unhide the annotation. // also describe that fields of java objects are not accessible from JS. } /** Loading
core/java/android/webkit/WebViewClassic.java +3 −0 Original line number Diff line number Diff line Loading @@ -4114,12 +4114,15 @@ public final class WebViewClassic implements WebViewProvider, WebViewProvider.Sc */ @Override public void addJavascriptInterface(Object object, String name) { if (object == null) { return; } WebViewCore.JSInterfaceData arg = new WebViewCore.JSInterfaceData(); // TODO in a separate CL provide logic to enable annotations for API level JB_MR1 and above. arg.mObject = object; arg.mInterfaceName = name; arg.mRequireAnnotation = false; mWebViewCore.sendMessage(EventHub.ADD_JS_INTERFACE, arg); } Loading
core/java/android/webkit/WebViewCore.java +2 −1 Original line number Diff line number Diff line Loading @@ -824,6 +824,7 @@ public final class WebViewCore { static class JSInterfaceData { Object mObject; String mInterfaceName; boolean mRequireAnnotation; } static class JSKeyData { Loading Loading @@ -1489,7 +1490,7 @@ public final class WebViewCore { case ADD_JS_INTERFACE: JSInterfaceData jsData = (JSInterfaceData) msg.obj; mBrowserFrame.addJavascriptInterface(jsData.mObject, jsData.mInterfaceName); jsData.mInterfaceName, jsData.mRequireAnnotation); break; case REMOVE_JS_INTERFACE: Loading