new json-rpc call for debug_metrics on advanced settings desktop tab;

include verify() bridge for desktop

Signed-off-by: Vitaliy Vlasov <siphiuel@gmail.com>
This commit is contained in:
Rob Culliton 2018-12-03 14:19:56 -05:00 committed by Vitaliy Vlasov
parent 9f7d32b1c5
commit a04952b60c
No known key found for this signature in database
GPG Key ID: A7D57C347F2B2964
9 changed files with 160 additions and 45 deletions

View File

@ -92,15 +92,7 @@ void RCTStatus::startNode(QString configString) {
if (!relativeDataDirPath.startsWith("/")) if (!relativeDataDirPath.startsWith("/"))
relativeDataDirPath.prepend("/"); relativeDataDirPath.prepend("/");
QString statusDataDir = qgetenv("STATUS_DATA_DIR"); QString rootDirPath = getRootDirPath();
QString rootDirPath;
if (!statusDataDir.isEmpty()) {
rootDirPath = statusDataDir;
}
else {
rootDirPath = QStandardPaths::writableLocation(QStandardPaths::AppLocalDataLocation);
}
QDir rootDir(rootDirPath); QDir rootDir(rootDirPath);
QString absDataDirPath = rootDirPath + relativeDataDirPath; QString absDataDirPath = rootDirPath + relativeDataDirPath;
QDir dataDir(absDataDirPath); QDir dataDir(absDataDirPath);
@ -181,6 +173,19 @@ void RCTStatus::login(QString address, QString password, double callbackId) {
}, address, password, callbackId); }, address, password, callbackId);
} }
void RCTStatus::verify(QString address, QString password, double callbackId) {
Q_D(RCTStatus);
qCInfo(RCTSTATUS) << "::verify call - callbackId:" << callbackId;
QtConcurrent::run([&](QString address, QString password, double callbackId) {
QDir rootDir(getRootDirPath());
QString keystorePath = rootDir.absoluteFilePath("keystore");
const char* result = VerifyAccountPassword(keystorePath.toUtf8().data(), address.toUtf8().data(), password.toUtf8().data());
logStatusGoResult("::verify VerifyAccountPassword", result);
d->bridge->invokePromiseCallback(callbackId, QVariantList{result});
}, address, password, callbackId);
}
void RCTStatus::sendTransaction(QString txArgsJSON, QString password, double callbackId) { void RCTStatus::sendTransaction(QString txArgsJSON, QString password, double callbackId) {
Q_D(RCTStatus); Q_D(RCTStatus);
@ -329,3 +334,17 @@ void RCTStatus::updateMailservers(QString enodes, double callbackId) {
d->bridge->invokePromiseCallback(callbackId, QVariantList{result}); d->bridge->invokePromiseCallback(callbackId, QVariantList{result});
}, enodes, callbackId); }, enodes, callbackId);
} }
QString RCTStatus::getRootDirPath() {
QString statusDataDir = qgetenv("STATUS_DATA_DIR");
QString rootDirPath;
if (!statusDataDir.isEmpty()) {
rootDirPath = statusDataDir;
}
else {
rootDirPath = QStandardPaths::writableLocation(QStandardPaths::AppLocalDataLocation);
}
return rootDirPath;
}

View File

@ -42,6 +42,7 @@ public:
Q_INVOKABLE void addPeer(QString enode, double callbackId); Q_INVOKABLE void addPeer(QString enode, double callbackId);
Q_INVOKABLE void recoverAccount(QString passphrase, QString password, double callbackId); Q_INVOKABLE void recoverAccount(QString passphrase, QString password, double callbackId);
Q_INVOKABLE void login(QString address, QString password, double callbackId); Q_INVOKABLE void login(QString address, QString password, double callbackId);
Q_INVOKABLE void verify(QString address, QString password, double callbackId);
Q_INVOKABLE void sendTransaction(QString txArgsJSON, QString password, double callbackId); Q_INVOKABLE void sendTransaction(QString txArgsJSON, QString password, double callbackId);
Q_INVOKABLE void signMessage(QString rpcParams, double callbackId); Q_INVOKABLE void signMessage(QString rpcParams, double callbackId);
Q_INVOKABLE void signGroupMembership(QString content, double callbackId); Q_INVOKABLE void signGroupMembership(QString content, double callbackId);
@ -74,6 +75,7 @@ private Q_SLOTS:
private: private:
void logStatusGoResult(const char* methodName, const char* result); void logStatusGoResult(const char* methodName, const char* result);
QString getRootDirPath();
QScopedPointer<RCTStatusPrivate> d_ptr; QScopedPointer<RCTStatusPrivate> d_ptr;
}; };

View File

@ -229,6 +229,7 @@
(def ^:const api-response "api-response") (def ^:const api-response "api-response")
(def ^:const api-request "api-request") (def ^:const api-request "api-request")
(def ^:const history-state-changed "history-state-changed") (def ^:const history-state-changed "history-state-changed")
(def ^:const debug-metrics "debug_metrics")
(def ^:const web3-send-async "web3-send-async") (def ^:const web3-send-async "web3-send-async")
(def ^:const web3-send-async-read-only "web3-send-async-read-only") (def ^:const web3-send-async-read-only "web3-send-async-read-only")
(def ^:const web3-send-async-callback "web3-send-async-callback") (def ^:const web3-send-async-callback "web3-send-async-callback")

View File

@ -13,6 +13,7 @@
[clojure.string :as string] [clojure.string :as string]
[status-im.data-store.mailservers :as data-store.mailservers] [status-im.data-store.mailservers :as data-store.mailservers]
[status-im.i18n :as i18n] [status-im.i18n :as i18n]
[status-im.utils.handlers :as handlers]
[status-im.accounts.update.core :as accounts.update] [status-im.accounts.update.core :as accounts.update]
[status-im.ui.screens.navigation :as navigation])) [status-im.ui.screens.navigation :as navigation]))
@ -94,37 +95,9 @@
db db
mailservers)}) mailservers)})
(defn- parse-json
;; NOTE(dmitryn) Expects JSON response like:
;; {"error": "msg"} or {"result": true}
[s]
(try
(let [res (-> s
js/JSON.parse
(js->clj :keywordize-keys true))]
;; NOTE(dmitryn): AddPeer() may return {"error": ""}
;; assuming empty error is a success response
;; by transforming {"error": ""} to {:result true}
(if (and (:error res)
(= (:error res) ""))
{:result true}
res))
(catch :default e
{:error (.-message e)})))
(defn- response-handler [success-fn error-fn]
(fn handle-response
([response]
(let [{:keys [error result]} (parse-json response)]
(handle-response error result)))
([error result]
(if error
(error-fn error)
(success-fn result)))))
(defn add-peer! [enode] (defn add-peer! [enode]
(status/add-peer enode (status/add-peer enode
(response-handler #(log/debug "mailserver: add-peer success" %) (handlers/response-handler #(log/debug "mailserver: add-peer success" %)
#(log/error "mailserver: add-peer error" %)))) #(log/error "mailserver: add-peer error" %))))
;; We now wait for a confirmation from the mailserver before marking the message ;; We now wait for a confirmation from the mailserver before marking the message
@ -133,7 +106,7 @@
(defn update-mailservers! [enodes] (defn update-mailservers! [enodes]
(status/update-mailservers (status/update-mailservers
(.stringify js/JSON (clj->js enodes)) (.stringify js/JSON (clj->js enodes))
(response-handler #(log/debug "mailserver: update-mailservers success" %) (handlers/response-handler #(log/debug "mailserver: update-mailservers success" %)
#(log/error "mailserver: update-mailservers error" %)))) #(log/error "mailserver: update-mailservers error" %))))
(defn remove-peer! [enode] (defn remove-peer! [enode]
@ -143,7 +116,7 @@
:params [enode]} :params [enode]}
payload (.stringify js/JSON (clj->js args))] payload (.stringify js/JSON (clj->js args))]
(status/call-private-rpc payload (status/call-private-rpc payload
(response-handler #(log/debug "mailserver: remove-peer success" %) (handlers/response-handler #(log/debug "mailserver: remove-peer success" %)
#(log/error "mailserver: remove-peer error" %))))) #(log/error "mailserver: remove-peer error" %)))))
(re-frame/reg-fx (re-frame/reg-fx

View File

@ -2,6 +2,11 @@
(:require [status-im.utils.handlers :as handlers] (:require [status-im.utils.handlers :as handlers]
[status-im.utils.fx :as fx] [status-im.utils.fx :as fx]
[status-im.ui.screens.navigation :as navigation] [status-im.ui.screens.navigation :as navigation]
[status-im.constants :as constants]
[re-frame.core :as re-frame]
[status-im.native-module.core :as status]
[taoensso.timbre :as log]
[status-im.utils.handlers :as handlers]
[status-im.utils.platform :as platform])) [status-im.utils.platform :as platform]))
(fx/defn change-tab (fx/defn change-tab
@ -26,3 +31,37 @@
:show-desktop-tab :show-desktop-tab
(fn [cofx [_ tab-name]] (fn [cofx [_ tab-name]]
(show-desktop-tab cofx tab-name))) (show-desktop-tab cofx tab-name)))
(defn packet-keys [direction]
"helper for accessing deeply nested metrics keys"
{:pre [(#{:in :out} direction)]}
[:misc direction :packets :Overall])
(handlers/register-handler-fx
:debug-metrics-success
(fn [{:keys [db]} [_ {:keys [p2p mailserver les whisper], :as metrics}]]
{:db (assoc-in db
[:desktop/desktop :debug-metrics]
{:mailserver-request-process-time (get-in mailserver [:requestProcessTime :Overall])
:mailserver-request-errors (get-in mailserver [:requestErrors :Overall])
:les-packets-in (get-in les (packet-keys :in))
:les-packets-out (get-in les (packet-keys :out))
:p2p-inbound-traffic (get-in p2p [:InboundTraffic :Overall])
:p2p-outbound-traffic (get-in p2p [:OutboundTraffic :Overall])})}))
(defn debug-metrics-rpc-call [payload]
"json rpc wrapper for debug metrics; dispatch :debug-metrics-success on success"
(status/call-private-rpc
payload
(handlers/response-handler #(re-frame/dispatch [:debug-metrics-success %])
#(log/debug "we did not get the debug metrics" %))))
(handlers/register-handler-fx
:load-debug-metrics
(fn [{:keys [db]} _]
(let [args {:jsonrpc "2.0"
:id 2
:method constants/debug-metrics
:params [true]}
payload (.stringify js/JSON (clj->js args))]
(debug-metrics-rpc-call payload))))

View File

@ -164,6 +164,11 @@
:font-size 20}) :font-size 20})
(def connection-message-text (def connection-message-text
{:margin-left 24
:margin-bottom 10
:font-size 16})
(def connection-stats-entry
{:margin-left 24 {:margin-left 24
:margin-bottom 10}) :margin-bottom 10})
@ -177,5 +182,11 @@
:margin-bottom 16 :margin-bottom 16
:font-size 16}) :font-size 16})
(def connection-stats-title
{:margin-left 24
:margin-top 16
:margin-bottom 16
:font-size 16})
(def pair-button (def pair-button
{:margin-left 32}) {:margin-left 32})

View File

@ -15,6 +15,9 @@
[status-im.ui.screens.pairing.views :as pairing.views] [status-im.ui.screens.pairing.views :as pairing.views]
[status-im.ui.components.qr-code-viewer.views :as qr-code-viewer] [status-im.ui.components.qr-code-viewer.views :as qr-code-viewer]
[status-im.ui.screens.desktop.main.tabs.profile.styles :as styles] [status-im.ui.screens.desktop.main.tabs.profile.styles :as styles]
[status-im.native-module.core :as status]
[status-im.mailserver.core :as mailserver.core]
[status-im.constants :as constants]
[status-im.ui.screens.profile.user.views :as profile] [status-im.ui.screens.profile.user.views :as profile]
[status-im.ui.screens.profile.seed.views :as profile.recovery] [status-im.ui.screens.profile.seed.views :as profile.recovery]
[status-im.ui.components.common.common :as components.common])) [status-im.ui.components.common.common :as components.common]))
@ -99,6 +102,36 @@
(and peers-disconnected? searching?) "Disconnected and searching" (and peers-disconnected? searching?) "Disconnected and searching"
:else "Disconnected"))) :else "Disconnected")))
(defn connection-statistics-display
[{:keys [mailserver-request-process-time
mailserver-request-errors
les-packets-in
les-packets-out
p2p-inbound-traffic
p2p-outbound-traffic]}]
[react/view {:style {:flex-direction :row}}
[react/view
[react/text {:style styles/connection-stats-title}
"Mailserver requests"]
[react/text {:style styles/connection-stats-entry}
(str "errors " p2p-inbound-traffic)]
[react/text {:style styles/connection-stats-entry}
(str "process time " p2p-outbound-traffic)]]
[react/view
[react/text {:style styles/connection-stats-title}
"p2p traffic"]
[react/text {:style styles/connection-stats-entry}
(str "inbound " p2p-inbound-traffic)]
[react/text {:style styles/connection-stats-entry}
(str "outbound " p2p-outbound-traffic)]]
[react/view
[react/text {:style styles/connection-stats-title}
"LES packets"]
[react/text {:style styles/connection-stats-entry}
(str "inbound " les-packets-in)]
[react/text {:style styles/connection-stats-entry}
(str "outbound " les-packets-out)]]])
(views/defview advanced-settings [] (views/defview advanced-settings []
(views/letsubs [installations [:pairing/installations] (views/letsubs [installations [:pairing/installations]
current-mailserver-id [:mailserver/current-id] current-mailserver-id [:mailserver/current-id]
@ -106,6 +139,7 @@
mailserver-state [:mailserver/state] mailserver-state [:mailserver/state]
node-status [:node-status] node-status [:node-status]
peers-count [:peers-count] peers-count [:peers-count]
connection-stats [:connection-stats]
disconnected [:disconnected?]] disconnected [:disconnected?]]
(let [render-fn (offline-messaging.views/render-row current-mailserver-id) (let [render-fn (offline-messaging.views/render-row current-mailserver-id)
connection-message (connection-status peers-count node-status mailserver-state disconnected)] connection-message (connection-status peers-count node-status mailserver-state disconnected)]
@ -123,7 +157,9 @@
[react/view {:style {:margin-vertical 8}} [react/view {:style {:margin-vertical 8}}
[render-fn mailserver]])] [render-fn mailserver]])]
(when (config/pairing-enabled? true) (when (config/pairing-enabled? true)
(installations-section installations))]))) (installations-section installations))
[react/view {:style styles/title-separator}]
(connection-statistics-display connection-stats)])))
(views/defview backup-recovery-phrase [] (views/defview backup-recovery-phrase []
[profile.recovery/backup-seed]) [profile.recovery/backup-seed])
@ -161,7 +197,9 @@
:value notifications? :value notifications?
:on-value-change #(re-frame/dispatch [:accounts.ui/notifications-enabled (not notifications?)])}]] :on-value-change #(re-frame/dispatch [:accounts.ui/notifications-enabled (not notifications?)])}]]
[react/touchable-highlight {:style (styles/profile-row adv-settings-open?) [react/touchable-highlight {:style (styles/profile-row adv-settings-open?)
:on-press #(re-frame/dispatch [:navigate-to (if adv-settings-open? :home :advanced-settings)])} :on-press #(do
(re-frame/dispatch [:navigate-to (if adv-settings-open? :home :advanced-settings)])
(re-frame/dispatch [:load-debug-metrics]))}
[react/view {:style styles/adv-settings} [react/view {:style styles/adv-settings}
[react/text {:style (styles/profile-row-text colors/black) [react/text {:style (styles/profile-row-text colors/black)
:font (if adv-settings-open? :medium :default)} :font (if adv-settings-open? :medium :default)}

View File

@ -54,6 +54,10 @@
(fn [peers-count] (fn [peers-count]
(zero? peers-count))) (zero? peers-count)))
(reg-sub :connection-stats
(fn [db _]
(get-in db [:desktop/desktop :debug-metrics])))
(reg-sub :offline? (reg-sub :offline?
:<- [:network-status] :<- [:network-status]
:<- [:sync-state] :<- [:sync-state]

View File

@ -95,6 +95,34 @@
check-spec) check-spec)
(re-frame/inject-cofx :now)]) (re-frame/inject-cofx :now)])
(defn- parse-json
;; NOTE(dmitryn) Expects JSON response like:
;; {"error": "msg"} or {"result": true}
[s]
(try
(let [res (-> s
js/JSON.parse
(js->clj :keywordize-keys true))]
;; NOTE(dmitryn): AddPeer() may return {"error": ""}
;; assuming empty error is a success response
;; by transforming {"error": ""} to {:result true}
(if (and (:error res)
(= (:error res) ""))
{:result true}
res))
(catch :default e
{:error (.-message e)})))
(defn response-handler [success-fn error-fn]
(fn handle-response
([response]
(let [{:keys [error result]} (parse-json response)]
(handle-response error result)))
([error result]
(if error
(error-fn error)
(success-fn result)))))
(defn register-handler-fx (defn register-handler-fx
([name handler] ([name handler]
(register-handler-fx name nil handler)) (register-handler-fx name nil handler))