GeolocationPermissions.java revision 57534f1b9f52cea094e8197d1ca40f0d2f68cc66
10ac031b3d29c6de90895c875991585812dc7388fSteve Block/*
20ac031b3d29c6de90895c875991585812dc7388fSteve Block * Copyright (C) 2009 The Android Open Source Project
30ac031b3d29c6de90895c875991585812dc7388fSteve Block *
40ac031b3d29c6de90895c875991585812dc7388fSteve Block * Licensed under the Apache License, Version 2.0 (the "License");
50ac031b3d29c6de90895c875991585812dc7388fSteve Block * you may not use this file except in compliance with the License.
60ac031b3d29c6de90895c875991585812dc7388fSteve Block * You may obtain a copy of the License at
70ac031b3d29c6de90895c875991585812dc7388fSteve Block *
80ac031b3d29c6de90895c875991585812dc7388fSteve Block *      http://www.apache.org/licenses/LICENSE-2.0
90ac031b3d29c6de90895c875991585812dc7388fSteve Block *
100ac031b3d29c6de90895c875991585812dc7388fSteve Block * Unless required by applicable law or agreed to in writing, software
110ac031b3d29c6de90895c875991585812dc7388fSteve Block * distributed under the License is distributed on an "AS IS" BASIS,
120ac031b3d29c6de90895c875991585812dc7388fSteve Block * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
130ac031b3d29c6de90895c875991585812dc7388fSteve Block * See the License for the specific language governing permissions and
140ac031b3d29c6de90895c875991585812dc7388fSteve Block * limitations under the License.
150ac031b3d29c6de90895c875991585812dc7388fSteve Block */
160ac031b3d29c6de90895c875991585812dc7388fSteve Block
170ac031b3d29c6de90895c875991585812dc7388fSteve Blockpackage android.webkit;
180ac031b3d29c6de90895c875991585812dc7388fSteve Block
190ac031b3d29c6de90895c875991585812dc7388fSteve Blockimport android.os.Handler;
200ac031b3d29c6de90895c875991585812dc7388fSteve Blockimport android.os.Message;
210ac031b3d29c6de90895c875991585812dc7388fSteve Blockimport android.util.Log;
226c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roardimport java.util.HashMap;
23d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Blockimport java.util.HashSet;
246c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roardimport java.util.Map;
250ac031b3d29c6de90895c875991585812dc7388fSteve Blockimport java.util.Set;
260ac031b3d29c6de90895c875991585812dc7388fSteve Block
270ac031b3d29c6de90895c875991585812dc7388fSteve Block
280ac031b3d29c6de90895c875991585812dc7388fSteve Block/**
2957534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * This class is used to get Geolocation permissions from, and set them on the
3057534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * WebView. For example, it could be used to allow a user to manage Geolocation
3157534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * permissions from a browser's UI.
3257534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block *
3357534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * Permissions are managed on a per-origin basis, as required by the
3457534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * Geolocation spec - http://dev.w3.org/geo/api/spec-source.html. An origin
3557534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * specifies the scheme, host and port of particular frame. An origin is
3657534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * represented here as a string, using the output of
3757534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * WebCore::SecurityOrigin::toString.
3857534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block *
3957534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * This class is the Java counterpart of the WebKit C++ GeolocationPermissions
4057534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * class. It simply marshalls calls from the UI thread to the WebKit thread.
4157534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block *
4257534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * Within WebKit, Geolocation permissions may be applied either temporarily
4357534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * (for the duration of the page) or permanently. This class deals only with
4457534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block * permanent permissions.
450ac031b3d29c6de90895c875991585812dc7388fSteve Block */
460ac031b3d29c6de90895c875991585812dc7388fSteve Blockpublic final class GeolocationPermissions {
474faee09c422a70439129e9fb40dd82f03d42c98dSteve Block    /**
484faee09c422a70439129e9fb40dd82f03d42c98dSteve Block     * Callback interface used by the browser to report a Geolocation permission
494faee09c422a70439129e9fb40dd82f03d42c98dSteve Block     * state set by the user in response to a permissions prompt.
504faee09c422a70439129e9fb40dd82f03d42c98dSteve Block     */
514faee09c422a70439129e9fb40dd82f03d42c98dSteve Block    public interface Callback {
524faee09c422a70439129e9fb40dd82f03d42c98dSteve Block        public void invoke(String origin, boolean allow, boolean remember);
534faee09c422a70439129e9fb40dd82f03d42c98dSteve Block    };
544faee09c422a70439129e9fb40dd82f03d42c98dSteve Block
550ac031b3d29c6de90895c875991585812dc7388fSteve Block    // Log tag
560ac031b3d29c6de90895c875991585812dc7388fSteve Block    private static final String TAG = "geolocationPermissions";
570ac031b3d29c6de90895c875991585812dc7388fSteve Block
580ac031b3d29c6de90895c875991585812dc7388fSteve Block    // Global instance
590ac031b3d29c6de90895c875991585812dc7388fSteve Block    private static GeolocationPermissions sInstance;
600ac031b3d29c6de90895c875991585812dc7388fSteve Block
610ac031b3d29c6de90895c875991585812dc7388fSteve Block    private Handler mHandler;
626c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    private Handler mUIHandler;
630ac031b3d29c6de90895c875991585812dc7388fSteve Block
640ac031b3d29c6de90895c875991585812dc7388fSteve Block    // Members used to transfer the origins and permissions between threads.
650ac031b3d29c6de90895c875991585812dc7388fSteve Block    private Set<String> mOrigins;
660ac031b3d29c6de90895c875991585812dc7388fSteve Block    private boolean mAllowed;
67d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block    private Set<String> mOriginsToClear;
68d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block    private Set<String> mOriginsToAllow;
690ac031b3d29c6de90895c875991585812dc7388fSteve Block
700ac031b3d29c6de90895c875991585812dc7388fSteve Block    // Message ids
710ac031b3d29c6de90895c875991585812dc7388fSteve Block    static final int GET_ORIGINS = 0;
720ac031b3d29c6de90895c875991585812dc7388fSteve Block    static final int GET_ALLOWED = 1;
730ac031b3d29c6de90895c875991585812dc7388fSteve Block    static final int CLEAR = 2;
74d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block    static final int ALLOW = 3;
75d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block    static final int CLEAR_ALL = 4;
760ac031b3d29c6de90895c875991585812dc7388fSteve Block
776c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    // Message ids on the UI thread
786c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    static final int RETURN_ORIGINS = 0;
796c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    static final int RETURN_ALLOWED = 1;
806c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard
816c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    private static final String ORIGINS = "origins";
826c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    private static final String ORIGIN = "origin";
836c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    private static final String CALLBACK = "callback";
846c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    private static final String ALLOWED = "allowed";
856c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard
860ac031b3d29c6de90895c875991585812dc7388fSteve Block    /**
870ac031b3d29c6de90895c875991585812dc7388fSteve Block     * Gets the singleton instance of the class.
880ac031b3d29c6de90895c875991585812dc7388fSteve Block     */
890ac031b3d29c6de90895c875991585812dc7388fSteve Block    public static GeolocationPermissions getInstance() {
900ac031b3d29c6de90895c875991585812dc7388fSteve Block      if (sInstance == null) {
910ac031b3d29c6de90895c875991585812dc7388fSteve Block          sInstance = new GeolocationPermissions();
920ac031b3d29c6de90895c875991585812dc7388fSteve Block      }
930ac031b3d29c6de90895c875991585812dc7388fSteve Block      return sInstance;
940ac031b3d29c6de90895c875991585812dc7388fSteve Block    }
950ac031b3d29c6de90895c875991585812dc7388fSteve Block
960ac031b3d29c6de90895c875991585812dc7388fSteve Block    /**
976c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard     * Creates the UI message handler. Must be called on the UI thread.
982e4dbe70e7c0fe003dab0837fd1dba2703bdd6e2Mike LeBeau     * @hide
996c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard     */
1006c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    public void createUIHandler() {
1016c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        if (mUIHandler == null) {
1026c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            mUIHandler = new Handler() {
1036c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                @Override
1046c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                public void handleMessage(Message msg) {
1056c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                    // Runs on the UI thread.
1066c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                    switch (msg.what) {
1076c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                        case RETURN_ORIGINS: {
1086c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            Map values = (Map) msg.obj;
10957534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block                            Set<String> origins = (Set<String>) values.get(ORIGINS);
11057534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block                            ValueCallback<Set<String> > callback = (ValueCallback<Set<String> >) values.get(CALLBACK);
1116c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            callback.onReceiveValue(origins);
1126c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                        } break;
1136c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                        case RETURN_ALLOWED: {
1146c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            Map values = (Map) msg.obj;
1156c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            Boolean allowed = (Boolean) values.get(ALLOWED);
1166c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            ValueCallback<Boolean> callback = (ValueCallback<Boolean>) values.get(CALLBACK);
1176c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            callback.onReceiveValue(allowed);
1186c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                        } break;
1196c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                    }
1206c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                }
1216c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            };
1226c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        }
1236c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    }
1246c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard
1256c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    /**
1260ac031b3d29c6de90895c875991585812dc7388fSteve Block     * Creates the message handler. Must be called on the WebKit thread.
1272e4dbe70e7c0fe003dab0837fd1dba2703bdd6e2Mike LeBeau     * @hide
1280ac031b3d29c6de90895c875991585812dc7388fSteve Block     */
1290ac031b3d29c6de90895c875991585812dc7388fSteve Block    public void createHandler() {
1300ac031b3d29c6de90895c875991585812dc7388fSteve Block        if (mHandler == null) {
1310ac031b3d29c6de90895c875991585812dc7388fSteve Block            mHandler = new Handler() {
1320ac031b3d29c6de90895c875991585812dc7388fSteve Block                @Override
1330ac031b3d29c6de90895c875991585812dc7388fSteve Block                public void handleMessage(Message msg) {
1340ac031b3d29c6de90895c875991585812dc7388fSteve Block                    // Runs on the WebKit thread.
1350ac031b3d29c6de90895c875991585812dc7388fSteve Block                    switch (msg.what) {
1366c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                        case GET_ORIGINS: {
1370ac031b3d29c6de90895c875991585812dc7388fSteve Block                            getOriginsImpl();
1386c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            ValueCallback callback = (ValueCallback) msg.obj;
1396c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            Map values = new HashMap<String, Object>();
1406c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            values.put(CALLBACK, callback);
14157534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block                            values.put(ORIGINS, mOrigins);
1426c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            postUIMessage(Message.obtain(null, RETURN_ORIGINS, values));
1436c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            } break;
1446c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                        case GET_ALLOWED: {
1456c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            Map values = (Map) msg.obj;
1466c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            String origin = (String) values.get(ORIGIN);
1476c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            ValueCallback callback = (ValueCallback) values.get(CALLBACK);
1486c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            getAllowedImpl(origin);
1496c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            Map retValues = new HashMap<String, Object>();
1506c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            retValues.put(CALLBACK, callback);
1516c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            retValues.put(ALLOWED, new Boolean(mAllowed));
1526c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            postUIMessage(Message.obtain(null, RETURN_ALLOWED, retValues));
1536c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                            } break;
1540ac031b3d29c6de90895c875991585812dc7388fSteve Block                        case CLEAR:
1550ac031b3d29c6de90895c875991585812dc7388fSteve Block                            nativeClear((String) msg.obj);
1560ac031b3d29c6de90895c875991585812dc7388fSteve Block                            break;
157d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                        case ALLOW:
158d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                            nativeAllow((String) msg.obj);
159d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                            break;
1600ac031b3d29c6de90895c875991585812dc7388fSteve Block                        case CLEAR_ALL:
1610ac031b3d29c6de90895c875991585812dc7388fSteve Block                            nativeClearAll();
1620ac031b3d29c6de90895c875991585812dc7388fSteve Block                            break;
1630ac031b3d29c6de90895c875991585812dc7388fSteve Block                    }
1640ac031b3d29c6de90895c875991585812dc7388fSteve Block                }
1650ac031b3d29c6de90895c875991585812dc7388fSteve Block            };
166d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block
167d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            if (mOriginsToClear != null) {
168d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                for (String origin : mOriginsToClear) {
169d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                    nativeClear(origin);
170d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                }
171d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            }
172d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            if (mOriginsToAllow != null) {
173d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                for (String origin : mOriginsToAllow) {
174d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                    nativeAllow(origin);
175d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                }
176d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            }
1770ac031b3d29c6de90895c875991585812dc7388fSteve Block        }
1780ac031b3d29c6de90895c875991585812dc7388fSteve Block    }
1790ac031b3d29c6de90895c875991585812dc7388fSteve Block
1800ac031b3d29c6de90895c875991585812dc7388fSteve Block    /**
1810ac031b3d29c6de90895c875991585812dc7388fSteve Block     * Utility function to send a message to our handler.
1820ac031b3d29c6de90895c875991585812dc7388fSteve Block     */
1830ac031b3d29c6de90895c875991585812dc7388fSteve Block    private void postMessage(Message msg) {
1840ac031b3d29c6de90895c875991585812dc7388fSteve Block        assert(mHandler != null);
1850ac031b3d29c6de90895c875991585812dc7388fSteve Block        mHandler.sendMessage(msg);
1860ac031b3d29c6de90895c875991585812dc7388fSteve Block    }
1870ac031b3d29c6de90895c875991585812dc7388fSteve Block
1880ac031b3d29c6de90895c875991585812dc7388fSteve Block    /**
1896c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard     * Utility function to send a message to the handler on the UI thread
1906c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard     */
1916c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    private void postUIMessage(Message msg) {
1926c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        if (mUIHandler != null) {
1936c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            mUIHandler.sendMessage(msg);
1946c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        }
1956c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    }
1966c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard
1976c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    /**
1980ac031b3d29c6de90895c875991585812dc7388fSteve Block     * Gets the set of origins for which Geolocation permissions are stored.
1990ac031b3d29c6de90895c875991585812dc7388fSteve Block     * Note that we represent the origins as strings. These are created using
2000ac031b3d29c6de90895c875991585812dc7388fSteve Block     * WebCore::SecurityOrigin::toString(). As long as all 'HTML 5 modules'
20157534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block     * (Database, Geolocation etc) do so, it's safe to match up origins based
20257534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block     * on this string.
20357534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block     *
20457534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block     * Callback is a ValueCallback object whose onReceiveValue method will be
20557534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block     * called asynchronously with the set of origins.
2060ac031b3d29c6de90895c875991585812dc7388fSteve Block     */
20757534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block    public void getOrigins(ValueCallback<Set<String> > callback) {
2086c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        if (callback != null) {
2096c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            if (WebViewCore.THREAD_NAME.equals(Thread.currentThread().getName())) {
2106c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                getOriginsImpl();
21157534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block                callback.onReceiveValue(mOrigins);
2126c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            } else {
2136c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard                postMessage(Message.obtain(null, GET_ORIGINS, callback));
2140ac031b3d29c6de90895c875991585812dc7388fSteve Block            }
2150ac031b3d29c6de90895c875991585812dc7388fSteve Block        }
2160ac031b3d29c6de90895c875991585812dc7388fSteve Block    }
2170ac031b3d29c6de90895c875991585812dc7388fSteve Block
2180ac031b3d29c6de90895c875991585812dc7388fSteve Block    /**
2190ac031b3d29c6de90895c875991585812dc7388fSteve Block     * Helper method to get the set of origins.
2200ac031b3d29c6de90895c875991585812dc7388fSteve Block     */
2210ac031b3d29c6de90895c875991585812dc7388fSteve Block    private void getOriginsImpl() {
2220ac031b3d29c6de90895c875991585812dc7388fSteve Block        // Called on the WebKit thread.
2230ac031b3d29c6de90895c875991585812dc7388fSteve Block        mOrigins = nativeGetOrigins();
2240ac031b3d29c6de90895c875991585812dc7388fSteve Block    }
2250ac031b3d29c6de90895c875991585812dc7388fSteve Block
2260ac031b3d29c6de90895c875991585812dc7388fSteve Block    /**
2270ac031b3d29c6de90895c875991585812dc7388fSteve Block     * Gets the permission state for the specified origin.
22857534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block     *
22957534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block     * Callback is a ValueCallback object whose onReceiveValue method will be
23057534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block     * called asynchronously with the permission state for the origin.
2310ac031b3d29c6de90895c875991585812dc7388fSteve Block     */
2326c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard    public void getAllowed(String origin, ValueCallback<Boolean> callback) {
2336c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        if (callback == null) {
2346c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            return;
2356c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        }
2366c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        if (origin == null) {
2376c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            callback.onReceiveValue(null);
2386c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            return;
2396c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        }
2406c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        if (WebViewCore.THREAD_NAME.equals(Thread.currentThread().getName())) {
2416c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            getAllowedImpl(origin);
2426c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            callback.onReceiveValue(new Boolean(mAllowed));
2436c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard        } else {
2446c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            Map values = new HashMap<String, Object>();
2456c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            values.put(ORIGIN, origin);
2466c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            values.put(CALLBACK, callback);
2476c24b4d10223cb522e6bdbf0e334f61e672f4366Nicolas Roard            postMessage(Message.obtain(null, GET_ALLOWED, values));
2480ac031b3d29c6de90895c875991585812dc7388fSteve Block        }
2490ac031b3d29c6de90895c875991585812dc7388fSteve Block    }
2500ac031b3d29c6de90895c875991585812dc7388fSteve Block
2510ac031b3d29c6de90895c875991585812dc7388fSteve Block    /**
25257534f1b9f52cea094e8197d1ca40f0d2f68cc66Steve Block     * Helper method to get the permission state for the specified origin.
2530ac031b3d29c6de90895c875991585812dc7388fSteve Block     */
2540ac031b3d29c6de90895c875991585812dc7388fSteve Block    private void getAllowedImpl(String origin) {
2550ac031b3d29c6de90895c875991585812dc7388fSteve Block        // Called on the WebKit thread.
2560ac031b3d29c6de90895c875991585812dc7388fSteve Block        mAllowed = nativeGetAllowed(origin);
2570ac031b3d29c6de90895c875991585812dc7388fSteve Block    }
2580ac031b3d29c6de90895c875991585812dc7388fSteve Block
2590ac031b3d29c6de90895c875991585812dc7388fSteve Block    /**
260d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block     * Clears the permission state for the specified origin. This method may be
261d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block     * called before the WebKit thread has intialized the message handler.
262d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block     * Messages will be queued until this time.
2630ac031b3d29c6de90895c875991585812dc7388fSteve Block     */
2640ac031b3d29c6de90895c875991585812dc7388fSteve Block    public void clear(String origin) {
2650ac031b3d29c6de90895c875991585812dc7388fSteve Block        // Called on the UI thread.
266d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block        if (mHandler == null) {
267d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            if (mOriginsToClear == null) {
268d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                mOriginsToClear = new HashSet<String>();
269d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            }
270d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            mOriginsToClear.add(origin);
271d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            if (mOriginsToAllow != null) {
272d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                mOriginsToAllow.remove(origin);
273d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            }
274d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block        } else {
275d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            postMessage(Message.obtain(null, CLEAR, origin));
276d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block        }
277d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block    }
278d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block
279d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block    /**
280d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block     * Allows the specified origin. This method may be called before the WebKit
281d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block     * thread has intialized the message handler. Messages will be queued until
282d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block     * this time.
283d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block     */
284d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block    public void allow(String origin) {
285d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block        // Called on the UI thread.
286d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block        if (mHandler == null) {
287d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            if (mOriginsToAllow == null) {
288d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                mOriginsToAllow = new HashSet<String>();
289d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            }
290d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            mOriginsToAllow.add(origin);
291d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            if (mOriginsToClear != null) {
292d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block                mOriginsToClear.remove(origin);
293d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            }
294d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block        } else {
295d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block            postMessage(Message.obtain(null, ALLOW, origin));
296d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block        }
2970ac031b3d29c6de90895c875991585812dc7388fSteve Block    }
2980ac031b3d29c6de90895c875991585812dc7388fSteve Block
2990ac031b3d29c6de90895c875991585812dc7388fSteve Block    /**
3000ac031b3d29c6de90895c875991585812dc7388fSteve Block     * Clears the permission state for all origins.
3010ac031b3d29c6de90895c875991585812dc7388fSteve Block     */
3020ac031b3d29c6de90895c875991585812dc7388fSteve Block    public void clearAll() {
3030ac031b3d29c6de90895c875991585812dc7388fSteve Block        // Called on the UI thread.
3040ac031b3d29c6de90895c875991585812dc7388fSteve Block        postMessage(Message.obtain(null, CLEAR_ALL));
3050ac031b3d29c6de90895c875991585812dc7388fSteve Block    }
3060ac031b3d29c6de90895c875991585812dc7388fSteve Block
3070ac031b3d29c6de90895c875991585812dc7388fSteve Block    // Native functions, run on the WebKit thread.
3080ac031b3d29c6de90895c875991585812dc7388fSteve Block    private static native Set nativeGetOrigins();
3090ac031b3d29c6de90895c875991585812dc7388fSteve Block    private static native boolean nativeGetAllowed(String origin);
3100ac031b3d29c6de90895c875991585812dc7388fSteve Block    private static native void nativeClear(String origin);
311d875ce6dac3c2e9a671c121c80b40d2536cbb2afSteve Block    private static native void nativeAllow(String origin);
3120ac031b3d29c6de90895c875991585812dc7388fSteve Block    private static native void nativeClearAll();
3130ac031b3d29c6de90895c875991585812dc7388fSteve Block}
314