Introduce extended DApp API [#5042]
Signed-off-by: Andrey Shovkoplyas <motor4ik@gmail.com>
This commit is contained in:
parent
2e57b1b8cf
commit
61374add53
|
@ -1,20 +1,40 @@
|
|||
(function () {
|
||||
function bridgeSend(data){
|
||||
WebViewBridge.send(JSON.stringify(data));
|
||||
}
|
||||
|
||||
var history = window.history;
|
||||
var pushState = history.pushState;
|
||||
history.pushState = function(state) {
|
||||
setTimeout(function () {
|
||||
WebViewBridge.send(JSON.stringify({
|
||||
type: 'navStateChange',
|
||||
navState: { url: location.href, title: document.title }
|
||||
}))
|
||||
bridgeSend({
|
||||
type: 'history-state-changed',
|
||||
navState: { url: location.href, title: document.title }
|
||||
});
|
||||
}, 100);
|
||||
return pushState.apply(history, arguments);
|
||||
};
|
||||
|
||||
WebViewBridge.onMessage = function (messageString) {
|
||||
console.log("received from react-native: " + messageString);
|
||||
window.addEventListener('message', function (event) {
|
||||
if (!event.data || !event.data.type) { return; }
|
||||
if (event.data.type === 'STATUS_API_REQUEST') {
|
||||
bridgeSend({
|
||||
type: 'status-api-request',
|
||||
permissions: event.data.permissions,
|
||||
host: window.location.hostname
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
if (messageString === "navigate-to-blank")
|
||||
WebViewBridge.onMessage = function (message) {
|
||||
|
||||
data = JSON.parse(message);
|
||||
|
||||
if (data.type === "navigate-to-blank")
|
||||
window.location.href = "about:blank";
|
||||
|
||||
else if (data.type === "status-api-success")
|
||||
window.STATUS_API = data.data;
|
||||
window.postMessage({ type: 'STATUS_API_SUCCESS', permissions: data.keys }, "*");
|
||||
};
|
||||
}());
|
||||
|
|
|
@ -247,3 +247,8 @@
|
|||
(ethereum/sha3 "Transfer(address,address,uint256)"))
|
||||
|
||||
(def regx-emoji #"^((?:[\u261D\u26F9\u270A-\u270D]|\uD83C[\uDF85\uDFC2-\uDFC4\uDFC7\uDFCA-\uDFCC]|\uD83D[\uDC42\uDC43\uDC46-\uDC50\uDC66-\uDC69\uDC6E\uDC70-\uDC78\uDC7C\uDC81-\uDC83\uDC85-\uDC87\uDCAA\uDD74\uDD75\uDD7A\uDD90\uDD95\uDD96\uDE45-\uDE47\uDE4B-\uDE4F\uDEA3\uDEB4-\uDEB6\uDEC0\uDECC]|\uD83E[\uDD18-\uDD1C\uDD1E\uDD1F\uDD26\uDD30-\uDD39\uDD3D\uDD3E\uDDD1-\uDDDD])(?:\uD83C[\uDFFB-\uDFFF])?|(?:[\u231A\u231B\u23E9-\u23EC\u23F0\u23F3\u25FD\u25FE\u2614\u2615\u2648-\u2653\u267F\u2693\u26A1\u26AA\u26AB\u26BD\u26BE\u26C4\u26C5\u26CE\u26D4\u26EA\u26F2\u26F3\u26F5\u26FA\u26FD\u2705\u270A\u270B\u2728\u274C\u274E\u2753-\u2755\u2757\u2795-\u2797\u27B0\u27BF\u2B1B\u2B1C\u2B50\u2B55]|\uD83C[\uDC04\uDCCF\uDD8E\uDD91-\uDD9A\uDDE6-\uDDFF\uDE01\uDE1A\uDE2F\uDE32-\uDE36\uDE38-\uDE3A\uDE50\uDE51\uDF00-\uDF20\uDF2D-\uDF35\uDF37-\uDF7C\uDF7E-\uDF93\uDFA0-\uDFCA\uDFCF-\uDFD3\uDFE0-\uDFF0\uDFF4\uDFF8-\uDFFF]|\uD83D[\uDC00-\uDC3E\uDC40\uDC42-\uDCFC\uDCFF-\uDD3D\uDD4B-\uDD4E\uDD50-\uDD67\uDD7A\uDD95\uDD96\uDDA4\uDDFB-\uDE4F\uDE80-\uDEC5\uDECC\uDED0-\uDED2\uDEEB\uDEEC\uDEF4-\uDEF8]|\uD83E[\uDD10-\uDD3A\uDD3C-\uDD3E\uDD40-\uDD45\uDD47-\uDD4C\uDD50-\uDD6B\uDD80-\uDD97\uDDC0\uDDD0-\uDDE6])|(?:[#\*0-9\xA9\xAE\u203C\u2049\u2122\u2139\u2194-\u2199\u21A9\u21AA\u231A\u231B\u2328\u23CF\u23E9-\u23F3\u23F8-\u23FA\u24C2\u25AA\u25AB\u25B6\u25C0\u25FB-\u25FE\u2600-\u2604\u260E\u2611\u2614\u2615\u2618\u261D\u2620\u2622\u2623\u2626\u262A\u262E\u262F\u2638-\u263A\u2640\u2642\u2648-\u2653\u2660\u2663\u2665\u2666\u2668\u267B\u267F\u2692-\u2697\u2699\u269B\u269C\u26A0\u26A1\u26AA\u26AB\u26B0\u26B1\u26BD\u26BE\u26C4\u26C5\u26C8\u26CE\u26CF\u26D1\u26D3\u26D4\u26E9\u26EA\u26F0-\u26F5\u26F7-\u26FA\u26FD\u2702\u2705\u2708-\u270D\u270F\u2712\u2714\u2716\u271D\u2721\u2728\u2733\u2734\u2744\u2747\u274C\u274E\u2753-\u2755\u2757\u2763\u2764\u2795-\u2797\u27A1\u27B0\u27BF\u2934\u2935\u2B05-\u2B07\u2B1B\u2B1C\u2B50\u2B55\u3030\u303D\u3297\u3299]|\uD83C[\uDC04\uDCCF\uDD70\uDD71\uDD7E\uDD7F\uDD8E\uDD91-\uDD9A\uDDE6-\uDDFF\uDE01\uDE02\uDE1A\uDE2F\uDE32-\uDE3A\uDE50\uDE51\uDF00-\uDF21\uDF24-\uDF93\uDF96\uDF97\uDF99-\uDF9B\uDF9E-\uDFF0\uDFF3-\uDFF5\uDFF7-\uDFFF]|\uD83D[\uDC00-\uDCFD\uDCFF-\uDD3D\uDD49-\uDD4E\uDD50-\uDD67\uDD6F\uDD70\uDD73-\uDD7A\uDD87\uDD8A-\uDD8D\uDD90\uDD95\uDD96\uDDA4\uDDA5\uDDA8\uDDB1\uDDB2\uDDBC\uDDC2-\uDDC4\uDDD1-\uDDD3\uDDDC-\uDDDE\uDDE1\uDDE3\uDDE8\uDDEF\uDDF3\uDDFA-\uDE4F\uDE80-\uDEC5\uDECB-\uDED2\uDEE0-\uDEE5\uDEE9\uDEEB\uDEEC\uDEF0\uDEF3-\uDEF8]|\uD83E[\uDD10-\uDD3A\uDD3C-\uDD3E\uDD40-\uDD45\uDD47-\uDD4C\uDD50-\uDD6B\uDD80-\uDD97\uDDC0\uDDD0-\uDDE6])\uFE0F|[\t-\r \xA0\u1680\u2000-\u200A\u2028\u2029\u202F\u205F\u3000\uFEFF])+$")
|
||||
|
||||
(def ^:const dapp-permission-contact-code "CONTACT_CODE")
|
||||
(def ^:const status-api-success "status-api-success")
|
||||
(def ^:const status-api-request "status-api-request")
|
||||
(def ^:const history-state-changed "history-state-changed")
|
|
@ -0,0 +1,16 @@
|
|||
(ns status-im.data-store.dapp-permissions
|
||||
(:require [re-frame.core :as re-frame]
|
||||
[status-im.data-store.realm.core :as core]))
|
||||
|
||||
(re-frame/reg-cofx
|
||||
:data-store/all-dapp-permissions
|
||||
(fn [cofx _]
|
||||
(assoc cofx :all-dapp-permissions (-> @core/account-realm
|
||||
(core/get-all :dapp-permissions)
|
||||
(core/all-clj :dapp-permissions)))))
|
||||
|
||||
(defn save-dapp-permissions
|
||||
"Returns tx function for saving dapp permissions"
|
||||
[permissions]
|
||||
(fn [realm]
|
||||
(core/create realm :dapp-permissions permissions true)))
|
|
@ -7,7 +7,8 @@
|
|||
[status-im.data-store.realm.schemas.account.v5.core :as v5]
|
||||
[status-im.data-store.realm.schemas.account.v6.core :as v6]
|
||||
[status-im.data-store.realm.schemas.account.v7.core :as v7]
|
||||
[status-im.data-store.realm.schemas.account.v8.core :as v8]))
|
||||
[status-im.data-store.realm.schemas.account.v8.core :as v8]
|
||||
[status-im.data-store.realm.schemas.account.v9.core :as v9]))
|
||||
|
||||
;; TODO(oskarth): Add failing test if directory vXX exists but isn't in schemas.
|
||||
|
||||
|
@ -35,4 +36,7 @@
|
|||
:migration v7/migration}
|
||||
{:schema v8/schema
|
||||
:schemaVersion 8
|
||||
:migration v8/migration}])
|
||||
:migration v8/migration}
|
||||
{:schema v9/schema
|
||||
:schemaVersion 9
|
||||
:migration v9/migration}])
|
||||
|
|
|
@ -0,0 +1,26 @@
|
|||
(ns status-im.data-store.realm.schemas.account.v9.core
|
||||
(:require [status-im.data-store.realm.schemas.account.v5.chat :as chat]
|
||||
[status-im.data-store.realm.schemas.account.v6.transport :as transport]
|
||||
[status-im.data-store.realm.schemas.account.v1.contact :as contact]
|
||||
[status-im.data-store.realm.schemas.account.v7.message :as message]
|
||||
[status-im.data-store.realm.schemas.account.v1.request :as request]
|
||||
[status-im.data-store.realm.schemas.account.v1.user-status :as user-status]
|
||||
[status-im.data-store.realm.schemas.account.v1.local-storage :as local-storage]
|
||||
[status-im.data-store.realm.schemas.account.v2.mailserver :as mailserver]
|
||||
[status-im.data-store.realm.schemas.account.v8.browser :as browser]
|
||||
[status-im.data-store.realm.schemas.account.v9.dapp-permissions :as dapp-permissions]
|
||||
[taoensso.timbre :as log]))
|
||||
|
||||
(def schema [chat/schema
|
||||
transport/schema
|
||||
contact/schema
|
||||
message/schema
|
||||
request/schema
|
||||
mailserver/schema
|
||||
user-status/schema
|
||||
local-storage/schema
|
||||
browser/schema
|
||||
dapp-permissions/schema])
|
||||
|
||||
(defn migration [old-realm new-realm]
|
||||
(log/debug "migrating v9 account database: " old-realm new-realm))
|
|
@ -0,0 +1,7 @@
|
|||
(ns status-im.data-store.realm.schemas.account.v9.dapp-permissions)
|
||||
|
||||
(def schema {:name :dapp-permissions
|
||||
:primaryKey :dapp
|
||||
:properties {:dapp :string
|
||||
:permissions {:type "string[]"
|
||||
:optional true}}})
|
|
@ -1,5 +1,8 @@
|
|||
(ns status-im.models.browser
|
||||
(:require [status-im.data-store.browser :as browser-store]))
|
||||
(:require [status-im.data-store.browser :as browser-store]
|
||||
[status-im.data-store.dapp-permissions :as dapp-permissions]
|
||||
[status-im.i18n :as i18n]
|
||||
[status-im.constants :as constants]))
|
||||
|
||||
(defn get-current-url [{:keys [history history-index]}]
|
||||
(when (and history-index history)
|
||||
|
@ -23,7 +26,7 @@
|
|||
history (:history browser)
|
||||
history-url (try (nth history history-index) (catch js/Error _))]
|
||||
(when (not= history-url url)
|
||||
(let [slash? (= url (str history-url "/"))
|
||||
(let [slash? (= url (str history-url "/"))
|
||||
new-history (if slash?
|
||||
(assoc history history-index url)
|
||||
(conj (subvec history 0 (inc history-index)) url))
|
||||
|
@ -36,3 +39,38 @@
|
|||
(defn update-browser-and-navigate [cofx browser]
|
||||
(merge (update-browser-fx cofx browser)
|
||||
{:dispatch [:navigate-to :browser (:browser-id browser)]}))
|
||||
|
||||
(def permissions {constants/dapp-permission-contact-code {:label (i18n/label :t/your-contact-code)}})
|
||||
|
||||
(defn update-dapp-permissions-fx [{:keys [db]} permissions]
|
||||
{:db (assoc-in db [:dapps/permissions (:dapp permissions)] permissions)
|
||||
:data-store/tx [(dapp-permissions/save-dapp-permissions permissions)]})
|
||||
|
||||
(defn request-permission [cofx
|
||||
{:keys [dapp-name index requested-permissions permissions-allowed user-permissions
|
||||
permissions-data webview]
|
||||
:as params}]
|
||||
;; iterate all requested permissions
|
||||
(if (< index (count requested-permissions))
|
||||
(let [requested-permission (get requested-permissions index)]
|
||||
;; if requested permission exists and valid continue if not decline permission
|
||||
(if (and requested-permission (get permissions requested-permission))
|
||||
;; if permission already allowed go to next, if not, show confirmation dialog
|
||||
(if ((set user-permissions) requested-permission)
|
||||
{:dispatch [:next-dapp-permission params requested-permission permissions-data]}
|
||||
{:show-dapp-permission-confirmation-fx [requested-permission params]})
|
||||
{:dispatch [:next-dapp-permission params]}))
|
||||
(assoc (update-dapp-permissions-fx cofx {:dapp dapp-name
|
||||
:permissions (vec (set (concat (keys permissions-allowed)
|
||||
user-permissions)))})
|
||||
:send-to-bridge-fx [permissions-allowed webview])))
|
||||
|
||||
(defn next-permission [cofx params & [permission permissions-data]]
|
||||
(request-permission
|
||||
cofx
|
||||
(cond-> params
|
||||
true
|
||||
(update :index inc)
|
||||
|
||||
(and permission permissions-data)
|
||||
(assoc-in [:permissions-allowed permission] (get permissions-data permission)))))
|
|
@ -30,6 +30,7 @@
|
|||
:on "On"
|
||||
:off "Off"
|
||||
:mailserver-connection-error "Could not connect to mailserver"
|
||||
:dont-allow "Don't Allow"
|
||||
:custom "Custom"
|
||||
|
||||
:camera-access-error "To grant the required camera permission, please go to your system settings and make sure that Status > Camera is selected."
|
||||
|
@ -693,4 +694,7 @@
|
|||
:dapp "ÐApp"
|
||||
:selected "Selected"
|
||||
:selected-dapps "Selected ÐApps"
|
||||
:browser-warning "Connection is not proven secure. Make sure you trust this site before signing transactions or entering personal data."})
|
||||
:browser-warning "Connection is not proven secure. Make sure you trust this site before signing transactions or entering personal data."
|
||||
:make-sure-you-trust-dapp "Make sure that you trust this DApp"
|
||||
:would-like-to-access "Would like to Access"
|
||||
:your-contact-code "Your Contact Code"})
|
|
@ -3,10 +3,7 @@
|
|||
(:require [cljs.spec.alpha :as spec]))
|
||||
|
||||
(spec/def :browser/browser-id (spec/nilable string?))
|
||||
(spec/def :browser/contact (spec/nilable string?))
|
||||
(spec/def :browser/timestamp (spec/nilable int?))
|
||||
(spec/def :browser/url (spec/nilable string?))
|
||||
(spec/def :browser/photo-path (spec/nilable string?))
|
||||
(spec/def :browser/name (spec/nilable string?))
|
||||
(spec/def :browser/dapp? (spec/nilable boolean?))
|
||||
(spec/def :browser/error? (spec/nilable boolean?))
|
||||
|
@ -28,3 +25,13 @@
|
|||
:browser/history-index]))
|
||||
|
||||
(spec/def :browser/browsers (spec/nilable (spec/map-of :global/not-empty-string :browser/browser)))
|
||||
|
||||
(spec/def :dapp/dapp (spec/nilable string?))
|
||||
(spec/def :dapp/permissions (spec/nilable vector?))
|
||||
|
||||
(spec/def :dapp/permission-map
|
||||
(allowed-keys
|
||||
:req-un [:dapp/dapp]
|
||||
:opt-un [:dapp/permissions]))
|
||||
|
||||
(spec/def :dapps/permissions (spec/nilable (spec/map-of :global/not-empty-string :dapp/permission-map)))
|
|
@ -8,7 +8,10 @@
|
|||
[status-im.utils.universal-links.core :as utils.universal-links]
|
||||
[status-im.data-store.browser :as browser-store]
|
||||
[status-im.utils.http :as http]
|
||||
[status-im.models.browser :as model]))
|
||||
[status-im.models.browser :as model]
|
||||
[status-im.utils.platform :as platform]
|
||||
[status-im.utils.utils :as utils]
|
||||
[status-im.constants :as constants]))
|
||||
|
||||
(re-frame/reg-fx
|
||||
:browse
|
||||
|
@ -17,6 +20,25 @@
|
|||
(utils.universal-links/open! link)
|
||||
(list-selection/browse link))))
|
||||
|
||||
(re-frame/reg-fx
|
||||
:send-to-bridge-fx
|
||||
(fn [[permissions-allowed webview]]
|
||||
(.sendToBridge @webview (.stringify js/JSON (clj->js {:type constants/status-api-success
|
||||
:data permissions-allowed
|
||||
:keys (keys permissions-allowed)})))))
|
||||
|
||||
(re-frame/reg-fx
|
||||
:show-dapp-permission-confirmation-fx
|
||||
(fn [[permission {:keys [dapp-name permissions-data] :as params}]]
|
||||
(utils/show-confirmation
|
||||
{:ios-confirm-style "default"}
|
||||
(str "\"" dapp-name "\" " (i18n/label :t/would-like-to-access) " " (:label (get model/permissions permission)))
|
||||
(i18n/label :t/make-sure-you-trust-dapp)
|
||||
nil
|
||||
#(re-frame/dispatch [:next-dapp-permission params permission permissions-data])
|
||||
#(re-frame/dispatch [:next-dapp-permission params])
|
||||
(i18n/label :t/dont-allow))))
|
||||
|
||||
(handlers/register-handler-fx
|
||||
:initialize-browsers
|
||||
[(re-frame/inject-cofx :data-store/all-browsers)]
|
||||
|
@ -24,6 +46,13 @@
|
|||
(let [browsers (into {} (map #(vector (:browser-id %) %) all-stored-browsers))]
|
||||
{:db (assoc db :browser/browsers browsers)})))
|
||||
|
||||
(handlers/register-handler-fx
|
||||
:initialize-dapp-permissions
|
||||
[(re-frame/inject-cofx :data-store/all-dapp-permissions)]
|
||||
(fn [{:keys [db all-dapp-permissions]} _]
|
||||
(let [dapp-permissions (into {} (map #(vector (:dapp %) %) all-dapp-permissions))]
|
||||
{:db (assoc db :dapps/permissions dapp-permissions)})))
|
||||
|
||||
(handlers/register-handler-fx
|
||||
:browse-link-from-message
|
||||
(fn [_ [_ link]]
|
||||
|
@ -91,3 +120,31 @@
|
|||
(fn [cofx [{:keys [history-index] :as browser}]]
|
||||
(when (< history-index (dec (count (:history browser))))
|
||||
(nav-update-browser cofx browser (inc history-index)))))
|
||||
|
||||
(handlers/register-handler-fx
|
||||
:on-bridge-message
|
||||
[re-frame/trim-v]
|
||||
(fn [{:keys [db] :as cofx} [{{:keys [url]} :navState :keys [type host permissions]} browser webview]]
|
||||
(cond
|
||||
|
||||
(and (= type constants/history-state-changed) platform/ios? (not= "about:blank" url))
|
||||
(model/update-browser-history-fx cofx browser url false)
|
||||
|
||||
(= type constants/status-api-request)
|
||||
(let [{:account/keys [account]} db
|
||||
{:keys [dapp? name]} browser
|
||||
dapp-name (if dapp? name host)]
|
||||
(model/request-permission
|
||||
cofx
|
||||
{:dapp-name dapp-name
|
||||
:webview webview
|
||||
:index 0
|
||||
:user-permissions (get-in db [:dapps/permissions dapp-name :permissions])
|
||||
:requested-permissions permissions
|
||||
:permissions-data {constants/dapp-permission-contact-code (:public-key account)}})))))
|
||||
|
||||
(handlers/register-handler-fx
|
||||
:next-dapp-permission
|
||||
[re-frame/trim-v]
|
||||
(fn [cofx [params permission permissions-data]]
|
||||
(model/next-permission cofx params permission permissions-data)))
|
|
@ -18,7 +18,6 @@
|
|||
[status-im.ui.components.toolbar.actions :as actions]
|
||||
[status-im.ui.components.tooltip.views :as tooltip]
|
||||
[status-im.models.browser :as model]
|
||||
[status-im.utils.platform :as platform]
|
||||
[status-im.utils.http :as http]))
|
||||
|
||||
(views/defview toolbar-content-dapp [name]
|
||||
|
@ -67,13 +66,6 @@
|
|||
[react/view styles/web-view-loading
|
||||
[components/activity-indicator {:animating true}]]))
|
||||
|
||||
(defn on-bridge-message [message browser]
|
||||
(let [{:strs [type navState]} (js->clj (.parse js/JSON message))
|
||||
{:strs [url]} navState]
|
||||
(when (and platform/ios? (= type "navStateChange"))
|
||||
(when (not= "about:blank" url)
|
||||
(re-frame/dispatch [:update-browser-on-nav-change browser url false])))))
|
||||
|
||||
(defn on-navigation-change [event browser]
|
||||
(let [{:strs [url loading]} (js->clj event)]
|
||||
(when (not= "about:blank" url)
|
||||
|
@ -116,7 +108,11 @@
|
|||
:render-error web-view-error
|
||||
:render-loading web-view-loading
|
||||
:on-navigation-state-change #(on-navigation-change % browser)
|
||||
:on-bridge-message #(on-bridge-message % browser)
|
||||
:on-bridge-message #(re-frame/dispatch [:on-bridge-message
|
||||
(js->clj (.parse js/JSON %)
|
||||
:keywordize-keys true)
|
||||
browser
|
||||
webview])
|
||||
:on-load #(re-frame/dispatch [:update-browser-options {:error? false}])
|
||||
:on-error #(re-frame/dispatch [:update-browser-options {:error? true}])
|
||||
:injected-on-start-loading-java-script (str js-res/web3
|
||||
|
|
|
@ -207,7 +207,8 @@
|
|||
:transport/chats
|
||||
:transport/discovery-filter
|
||||
:desktop/desktop
|
||||
:dimensions/window]
|
||||
:dimensions/window
|
||||
:dapps/permissions]
|
||||
:opt-un
|
||||
[::current-public-key
|
||||
::modal
|
||||
|
|
|
@ -372,6 +372,7 @@
|
|||
[:load-contacts]
|
||||
[:initialize-chats]
|
||||
[:initialize-browsers]
|
||||
[:initialize-dapp-permissions]
|
||||
[:send-account-update-if-needed]
|
||||
[:process-pending-messages]
|
||||
[:update-wallet]
|
||||
|
|
|
@ -35,9 +35,6 @@
|
|||
(chat-events/start-chat chat-id {:navigation-replace? true})
|
||||
(input-events/select-chat-input-command send-command nil true)))))
|
||||
|
||||
(defn get-current-account [db]
|
||||
(:account/account db))
|
||||
|
||||
(defn valid-name? [name]
|
||||
(spec/valid? :profile/name name))
|
||||
|
||||
|
@ -101,7 +98,7 @@
|
|||
(handlers/register-handler-fx
|
||||
:my-profile/enter-two-random-words
|
||||
(fn [{:keys [db]} []]
|
||||
(let [{:keys [mnemonic]} (get-current-account db)
|
||||
(let [{:keys [mnemonic]} (:account/account db)
|
||||
shuffled-mnemonic (shuffle (map-indexed vector (clojure.string/split mnemonic #" ")))]
|
||||
{:db (assoc db :my-profile/seed {:step :first-word
|
||||
:first-word (first shuffled-mnemonic)
|
||||
|
|
|
@ -25,13 +25,16 @@
|
|||
(show-confirmation title content confirm-button-text on-accept nil))
|
||||
([title content confirm-button-text on-accept on-cancel]
|
||||
(show-confirmation nil title content confirm-button-text on-accept on-cancel))
|
||||
([{:keys [ios-confirm-style] :or {ios-confirm-style "destructive"}} title content confirm-button-text on-accept on-cancel]
|
||||
([ios-style title content confirm-button-text on-accept on-cancel]
|
||||
(show-confirmation ios-style title content confirm-button-text on-accept on-cancel nil))
|
||||
([{:keys [ios-confirm-style] :or {ios-confirm-style "destructive"}}
|
||||
title content confirm-button-text on-accept on-cancel cancel-button-text]
|
||||
(.alert (.-Alert rn-dependencies/react-native)
|
||||
title
|
||||
content
|
||||
;; Styles are only relevant on iOS. On Android first button is 'neutral' and second is 'positive'
|
||||
(clj->js
|
||||
(vector (merge {:text (i18n/label :t/cancel)
|
||||
(vector (merge {:text (or cancel-button-text (i18n/label :t/cancel))
|
||||
:style "cancel"
|
||||
:accessibility-label :cancel-button}
|
||||
(when on-cancel {:onPress on-cancel}))
|
||||
|
|
|
@ -17,7 +17,21 @@
|
|||
(re-frame/reg-cofx
|
||||
:data-store/all-browsers
|
||||
(fn [coeffects _]
|
||||
(assoc coeffects :all-stored-browsers []))))
|
||||
(assoc coeffects :all-stored-browsers [])))
|
||||
|
||||
(re-frame/reg-cofx
|
||||
:data-store/all-dapp-permissions
|
||||
(fn [coeffects _]
|
||||
(assoc coeffects :all-dapp-permissions [])))
|
||||
|
||||
(re-frame/reg-fx :send-to-bridge-fx #())
|
||||
|
||||
(re-frame/reg-fx
|
||||
:show-dapp-permission-confirmation-fx
|
||||
(fn [[permission {:keys [dapp-name permissions-data index] :as params}]]
|
||||
(if (and (= dapp-name "test.com") (#{0 1} index))
|
||||
(re-frame/dispatch [:next-dapp-permission params permission permissions-data])
|
||||
(re-frame/dispatch [:next-dapp-permission params])))))
|
||||
|
||||
(deftest browser-events
|
||||
|
||||
|
@ -63,8 +77,7 @@
|
|||
|
||||
(re-frame/dispatch [:open-browser (first (vals @browsers))])
|
||||
|
||||
(let [browser (re-frame/subscribe [:get-current-browser])
|
||||
options (re-frame/subscribe [:get :browser/options])
|
||||
(let [browser (re-frame/subscribe [:get-current-browser])
|
||||
dapp2-url2 (str dapp2-url "/nav2")
|
||||
dapp2-url3 (str dapp2-url "/nav3")]
|
||||
|
||||
|
@ -106,4 +119,67 @@
|
|||
(re-frame/dispatch [:browser-nav-forward @browser])
|
||||
|
||||
(is (= 1 (:history-index @browser)))
|
||||
(is (= [dapp2-url dapp2-url3] (:history @browser))))))))
|
||||
(is (= [dapp2-url dapp2-url3] (:history @browser))))))
|
||||
|
||||
(re-frame/dispatch [:initialize-dapp-permissions])
|
||||
|
||||
(let [dapps-permissions (re-frame/subscribe [:get :dapps/permissions])
|
||||
dapp-name "test.com"
|
||||
dapp-name2 "test2.org"]
|
||||
|
||||
(testing "dapps permissions"
|
||||
|
||||
(is (zero? (count @dapps-permissions)))
|
||||
|
||||
(re-frame/dispatch [:on-bridge-message {:type "status-api-request"
|
||||
:host dapp-name
|
||||
:permissions ["FAKE_PERMISSION"]}
|
||||
nil nil])
|
||||
|
||||
(is (= {:dapp dapp-name
|
||||
:permissions []}
|
||||
(get @dapps-permissions dapp-name)))
|
||||
|
||||
(re-frame/dispatch [:on-bridge-message {:type "status-api-request"
|
||||
:host dapp-name
|
||||
:permissions ["CONTACT_CODE"]}
|
||||
nil nil])
|
||||
|
||||
(is (= 1 (count @dapps-permissions)))
|
||||
|
||||
(is (= {:dapp dapp-name
|
||||
:permissions ["CONTACT_CODE"]}
|
||||
(get @dapps-permissions dapp-name)))
|
||||
|
||||
(re-frame/dispatch [:on-bridge-message {:type "status-api-request"
|
||||
:host dapp-name
|
||||
:permissions ["CONTACT_CODE" "FAKE_PERMISSION"]}
|
||||
nil nil])
|
||||
|
||||
(is (= 1 (count @dapps-permissions)))
|
||||
|
||||
(is (= {:dapp dapp-name
|
||||
:permissions ["CONTACT_CODE"]}
|
||||
(get @dapps-permissions dapp-name)))
|
||||
|
||||
(re-frame/dispatch [:on-bridge-message {:type "status-api-request"
|
||||
:host dapp-name
|
||||
:permissions ["FAKE_PERMISSION"]}
|
||||
nil nil])
|
||||
|
||||
(is (= 1 (count @dapps-permissions)))
|
||||
|
||||
(is (= {:dapp dapp-name
|
||||
:permissions ["CONTACT_CODE"]}
|
||||
(get @dapps-permissions dapp-name)))
|
||||
|
||||
(re-frame/dispatch [:on-bridge-message {:type "status-api-request"
|
||||
:host dapp-name2
|
||||
:permissions ["CONTACT_CODE"]}
|
||||
nil nil])
|
||||
|
||||
(is (= 2 (count @dapps-permissions)))
|
||||
|
||||
(is (= {:dapp dapp-name2
|
||||
:permissions []}
|
||||
(get @dapps-permissions dapp-name2)))))))
|
||||
|
|
Loading…
Reference in New Issue