mirror of
https://github.com/status-im/status-mobile.git
synced 2025-02-25 06:46:37 +00:00
Add profile pictures
Signed-off-by: Andrea Maria Piana <andrea.maria.piana@gmail.com>
This commit is contained in:
parent
09822e142b
commit
5643c4d537
BIN
resources/images/icons/tiny_edit@2x.png
Normal file
BIN
resources/images/icons/tiny_edit@2x.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 277 B |
BIN
resources/images/icons/tiny_edit@3x.png
Normal file
BIN
resources/images/icons/tiny_edit@3x.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 367 B |
@ -196,7 +196,7 @@
|
|||||||
group-contacts))
|
group-contacts))
|
||||||
|
|
||||||
:else users)
|
:else users)
|
||||||
{:keys [name preferred-name public-key photo-path]}
|
{:keys [name preferred-name public-key]}
|
||||||
(:multiaccount db)]
|
(:multiaccount db)]
|
||||||
(reduce
|
(reduce
|
||||||
(fn [acc [key {:keys [alias name identicon]}]]
|
(fn [acc [key {:keys [alias name identicon]}]]
|
||||||
@ -210,7 +210,6 @@
|
|||||||
public-key
|
public-key
|
||||||
{:alias name
|
{:alias name
|
||||||
:name (or preferred-name name)
|
:name (or preferred-name name)
|
||||||
:identicon photo-path
|
|
||||||
:public-key public-key})
|
:public-key public-key})
|
||||||
contacts)))
|
contacts)))
|
||||||
|
|
||||||
|
@ -4,8 +4,6 @@
|
|||||||
[status-im.data-store.contacts :as contacts-store]
|
[status-im.data-store.contacts :as contacts-store]
|
||||||
[status-im.ethereum.json-rpc :as json-rpc]
|
[status-im.ethereum.json-rpc :as json-rpc]
|
||||||
[status-im.mailserver.core :as mailserver]
|
[status-im.mailserver.core :as mailserver]
|
||||||
[status-im.multiaccounts.model :as multiaccounts.model]
|
|
||||||
[status-im.multiaccounts.update.core :as multiaccounts.update]
|
|
||||||
[status-im.transport.filters.core :as transport.filters]
|
[status-im.transport.filters.core :as transport.filters]
|
||||||
[status-im.tribute-to-talk.db :as tribute-to-talk]
|
[status-im.tribute-to-talk.db :as tribute-to-talk]
|
||||||
[status-im.tribute-to-talk.whitelist :as whitelist]
|
[status-im.tribute-to-talk.whitelist :as whitelist]
|
||||||
@ -44,17 +42,11 @@
|
|||||||
|
|
||||||
(defn- own-info
|
(defn- own-info
|
||||||
[db]
|
[db]
|
||||||
(let [{:keys [name preferred-name photo-path address]} (:multiaccount db)]
|
(let [{:keys [name preferred-name identicon address]} (:multiaccount db)]
|
||||||
{:name (or preferred-name name)
|
{:name (or preferred-name name)
|
||||||
:profile-image photo-path
|
:profile-image identicon
|
||||||
:address address}))
|
:address address}))
|
||||||
|
|
||||||
(fx/defn handle-update-from-contact-request [{:keys [db] :as cofx} {:keys [last-updated photo-path]}]
|
|
||||||
(when (> last-updated (get-in db [:multiaccount :last-updated]))
|
|
||||||
(fx/merge cofx
|
|
||||||
(multiaccounts.update/multiaccount-update :last-updated last-updated {:dont-sync? true})
|
|
||||||
(multiaccounts.update/multiaccount-update :photo-path photo-path {:dont-sync? true}))))
|
|
||||||
|
|
||||||
(fx/defn ensure-contacts
|
(fx/defn ensure-contacts
|
||||||
[{:keys [db]} contacts]
|
[{:keys [db]} contacts]
|
||||||
{:db (update db :contacts/contacts
|
{:db (update db :contacts/contacts
|
||||||
@ -126,37 +118,6 @@
|
|||||||
{:db (dissoc db :contacts/new-identity)}
|
{:db (dissoc db :contacts/new-identity)}
|
||||||
(upsert-contact contact)))))
|
(upsert-contact contact)))))
|
||||||
|
|
||||||
(fx/defn handle-contact-update
|
|
||||||
[{{:contacts/keys [contacts] :as db} :db :as cofx}
|
|
||||||
public-key
|
|
||||||
timestamp
|
|
||||||
{:keys [name profile-image address] :as m}]
|
|
||||||
;; We need to convert to timestamp ms as before we were using now in ms to
|
|
||||||
;; set last updated
|
|
||||||
;; Using whisper timestamp mostly works but breaks in a few scenarios:
|
|
||||||
;; 2 updates sent in the same second
|
|
||||||
;; when using multi-device & clocks are out of sync
|
|
||||||
;; Using logical clocks is probably the correct way to handle it, but an overkill
|
|
||||||
;; for now
|
|
||||||
(let [timestamp-ms (* timestamp 1000)
|
|
||||||
prev-last-updated (get-in db [:contacts/contacts public-key :last-updated])
|
|
||||||
current-public-key (multiaccounts.model/current-public-key cofx)]
|
|
||||||
(when (and (not= current-public-key public-key)
|
|
||||||
(< prev-last-updated timestamp-ms))
|
|
||||||
(let [contact (get contacts public-key)
|
|
||||||
|
|
||||||
;; Backward compatibility with <= 0.9.21, as they don't send
|
|
||||||
;; address in contact updates
|
|
||||||
contact-props
|
|
||||||
(cond-> {:public-key public-key
|
|
||||||
:photo-path profile-image
|
|
||||||
:name name
|
|
||||||
:last-updated timestamp-ms
|
|
||||||
:system-tags (conj (get contact :system-tags #{})
|
|
||||||
:contact/request-received)}
|
|
||||||
address (assoc :address address))]
|
|
||||||
(upsert-contact cofx contact-props)))))
|
|
||||||
|
|
||||||
(fx/defn initialize-contacts [cofx]
|
(fx/defn initialize-contacts [cofx]
|
||||||
(contacts-store/fetch-contacts-rpc cofx #(re-frame/dispatch [::contacts-loaded %])))
|
(contacts-store/fetch-contacts-rpc cofx #(re-frame/dispatch [::contacts-loaded %])))
|
||||||
|
|
||||||
|
@ -1,98 +1,2 @@
|
|||||||
(ns status-im.contact.core-test
|
(ns status-im.contact.core-test)
|
||||||
(:require [cljs.test :refer-macros [deftest is testing]]
|
|
||||||
[status-im.contact.core :as model]
|
|
||||||
[status-im.ethereum.json-rpc :as json-rpc]))
|
|
||||||
|
|
||||||
(def public-key "0x04fcf40c526b09ff9fb22f4a5dbd08490ef9b64af700870f8a0ba2133f4251d5607ed83cd9047b8c2796576bc83fa0de23a13a4dced07654b8ff137fe744047917")
|
|
||||||
|
|
||||||
(deftest handle-contact-update-test
|
|
||||||
(with-redefs [json-rpc/call (constantly nil)]
|
|
||||||
(testing "the contact is not in contacts"
|
|
||||||
(let [actual (model/handle-contact-update
|
|
||||||
{:db {}}
|
|
||||||
public-key
|
|
||||||
1
|
|
||||||
{:name "name"
|
|
||||||
:profile-image "image"})
|
|
||||||
contact (get-in actual [:db :contacts/contacts public-key])]
|
|
||||||
(testing "it adds a new contact"
|
|
||||||
(is (= {:public-key public-key
|
|
||||||
:photo-path "image"
|
|
||||||
:name "name"
|
|
||||||
:last-updated 1000
|
|
||||||
:system-tags #{:contact/request-received}}
|
|
||||||
contact)))))
|
|
||||||
(testing "the contact is already in contacts"
|
|
||||||
(testing "timestamp is greater than last-updated"
|
|
||||||
(let [actual (model/handle-contact-update
|
|
||||||
{:db {:contacts/contacts
|
|
||||||
{public-key {:public-key public-key
|
|
||||||
:photo-path "old-image"
|
|
||||||
:name "old-name"
|
|
||||||
:last-updated 0
|
|
||||||
:system-tags #{:contact/added}}}}}
|
|
||||||
public-key
|
|
||||||
1
|
|
||||||
{:name "new-name"
|
|
||||||
:profile-image "new-image"})
|
|
||||||
contact (get-in actual [:db :contacts/contacts public-key])]
|
|
||||||
(testing "it updates the contact and adds contact/request-received to system tags"
|
|
||||||
(is (= {:public-key public-key
|
|
||||||
:photo-path "new-image"
|
|
||||||
:name "new-name"
|
|
||||||
:last-updated 1000
|
|
||||||
|
|
||||||
:system-tags #{:contact/added :contact/request-received}}
|
|
||||||
contact)))))
|
|
||||||
(testing "timestamp is equal to last-updated"
|
|
||||||
(let [actual (model/handle-contact-update
|
|
||||||
{:db {:contacts/contacts
|
|
||||||
{public-key {:public-key public-key
|
|
||||||
:photo-path "old-image"
|
|
||||||
:name "old-name"
|
|
||||||
:last-updated 1000
|
|
||||||
:system-tags #{:contact/added}}}}}
|
|
||||||
public-key
|
|
||||||
1
|
|
||||||
{:name "new-name"
|
|
||||||
:profile-image "new-image"})]
|
|
||||||
(testing "it does nothing"
|
|
||||||
(is (nil? actual)))))
|
|
||||||
(testing "timestamp is less than last-updated"
|
|
||||||
(let [actual (model/handle-contact-update
|
|
||||||
{:db {:contacts/contacts
|
|
||||||
{public-key {:public-key public-key
|
|
||||||
:photo-path "old-image"
|
|
||||||
:name "old-name"
|
|
||||||
:last-updated 1000
|
|
||||||
:system-tags #{:contact/added :contact/request-received}}}}}
|
|
||||||
public-key
|
|
||||||
0
|
|
||||||
{:name "new-name"
|
|
||||||
:profile-image "new-image"})]
|
|
||||||
(testing "it does nothing"
|
|
||||||
(is (nil? actual))))))
|
|
||||||
(testing "backward compatibility"
|
|
||||||
(let [actual (model/handle-contact-update
|
|
||||||
{:db {:contacts/contacts
|
|
||||||
{public-key {:public-key public-key
|
|
||||||
:photo-path "old-image"
|
|
||||||
|
|
||||||
:name "old-name"
|
|
||||||
:last-updated 0
|
|
||||||
:system-tags #{:contact/added}}}}}
|
|
||||||
public-key
|
|
||||||
1
|
|
||||||
{:name "new-name"
|
|
||||||
:profile-image "new-image"})
|
|
||||||
contact (get-in actual [:db :contacts/contacts public-key])]
|
|
||||||
(testing "it updates the contact"
|
|
||||||
(is (= {:public-key public-key
|
|
||||||
:photo-path "new-image"
|
|
||||||
:name "new-name"
|
|
||||||
|
|
||||||
:last-updated 1000
|
|
||||||
:system-tags #{:contact/added :contact/request-received}} contact)))))
|
|
||||||
(testing "the message is coming from us"
|
|
||||||
(testing "it does not update contacts"
|
|
||||||
(is (nil? (model/handle-contact-update {:db {:multiaccount {:public-key "me"}}} "me" 1 {})))))))
|
|
||||||
|
@ -20,8 +20,8 @@
|
|||||||
(get contacts public-key
|
(get contacts public-key
|
||||||
(public-key->new-contact public-key))))
|
(public-key->new-contact public-key))))
|
||||||
|
|
||||||
(defn- contact-by-address [[_ contact] address]
|
(defn- contact-by-address [[addr contact] address]
|
||||||
(when (ethereum/address= (:address contact) address)
|
(when (ethereum/address= addr address)
|
||||||
contact))
|
contact))
|
||||||
|
|
||||||
(defn find-contact-by-address [contacts address]
|
(defn find-contact-by-address [contacts address]
|
||||||
@ -54,7 +54,7 @@
|
|||||||
[members admins contacts {:keys [public-key] :as current-account}]
|
[members admins contacts {:keys [public-key] :as current-account}]
|
||||||
(let [current-contact (some->
|
(let [current-contact (some->
|
||||||
current-account
|
current-account
|
||||||
(select-keys [:name :preferred-name :public-key :photo-path])
|
(select-keys [:name :preferred-name :public-key :identicon])
|
||||||
(clojure.set/rename-keys {:name :alias
|
(clojure.set/rename-keys {:name :alias
|
||||||
:preferred-name :name}))
|
:preferred-name :name}))
|
||||||
all-contacts (cond-> contacts
|
all-contacts (cond-> contacts
|
||||||
|
@ -13,21 +13,21 @@
|
|||||||
"0x048a2f8b80c60f89a91b4c1316e56f75b087f446e7b8701ceca06a40142d8efe1f5aa36bd0fee9e248060a8d5207b43ae98bef4617c18c71e66f920f324869c09f"}
|
"0x048a2f8b80c60f89a91b4c1316e56f75b087f446e7b8701ceca06a40142d8efe1f5aa36bd0fee9e248060a8d5207b43ae98bef4617c18c71e66f920f324869c09f"}
|
||||||
admins #{"0x04fcf40c526b09ff9fb22f4a5dbd08490ef9b64af700870f8a0ba2133f4251d5607ed83cd9047b8c2796576bc83fa0de23a13a4dced07654b8ff137fe744047917"}
|
admins #{"0x04fcf40c526b09ff9fb22f4a5dbd08490ef9b64af700870f8a0ba2133f4251d5607ed83cd9047b8c2796576bc83fa0de23a13a4dced07654b8ff137fe744047917"}
|
||||||
|
|
||||||
contacts {"0x04985040682b77a32bb4bb58268a0719bd24ca4d07c255153fe1eb2ccd5883669627bd1a092d7cc76e8e4b9104327667b19dcda3ac469f572efabe588c38c1985f"
|
contacts {"0x04985040682b77a32bb4bb58268a0719bd24ca4d07c255153fe1eb2ccd5883669627bd1a092d7cc76e8e4b9104327667b19dcda3ac469f572efabe588c38c1985f"
|
||||||
{:last-updated 0,
|
{:last-updated 0,
|
||||||
:name "User B",
|
:name "User B",
|
||||||
:photo-path "photo1",
|
:identicon "photo1",
|
||||||
:last-online 0,
|
:last-online 0,
|
||||||
:public-key
|
|
||||||
"0x04985040682b77a32bb4bb58268a0719bd24ca4d07c255153fe1eb2ccd5883669627bd1a092d7cc76e8e4b9104327667b19dcda3ac469f572efabe588c38c1985f"
|
|
||||||
:system-tags #{}}}
|
|
||||||
current-multiaccount {:last-updated 0,
|
|
||||||
:signed-up? true,
|
|
||||||
:sharing-usage-data? false,
|
|
||||||
:name "User A",
|
|
||||||
:photo-path "photo2",
|
|
||||||
:public-key
|
:public-key
|
||||||
"0x048a2f8b80c60f89a91b4c1316e56f75b087f446e7b8701ceca06a40142d8efe1f5aa36bd0fee9e248060a8d5207b43ae98bef4617c18c71e66f920f324869c09f"}]
|
"0x04985040682b77a32bb4bb58268a0719bd24ca4d07c255153fe1eb2ccd5883669627bd1a092d7cc76e8e4b9104327667b19dcda3ac469f572efabe588c38c1985f"
|
||||||
|
:system-tags #{}}}
|
||||||
|
current-multiaccount {:last-updated 0,
|
||||||
|
:signed-up? true,
|
||||||
|
:sharing-usage-data? false,
|
||||||
|
:name "User A",
|
||||||
|
:identicon "photo2",
|
||||||
|
:public-key
|
||||||
|
"0x048a2f8b80c60f89a91b4c1316e56f75b087f446e7b8701ceca06a40142d8efe1f5aa36bd0fee9e248060a8d5207b43ae98bef4617c18c71e66f920f324869c09f"}]
|
||||||
(is (= (contact.db/get-all-contacts-in-group-chat chat-contact-ids
|
(is (= (contact.db/get-all-contacts-in-group-chat chat-contact-ids
|
||||||
admins
|
admins
|
||||||
contacts
|
contacts
|
||||||
@ -39,11 +39,11 @@
|
|||||||
:public-key "0x04fcf40c526b09ff9fb22f4a5dbd08490ef9b64af700870f8a0ba2133f4251d5607ed83cd9047b8c2796576bc83fa0de23a13a4dced07654b8ff137fe744047917"
|
:public-key "0x04fcf40c526b09ff9fb22f4a5dbd08490ef9b64af700870f8a0ba2133f4251d5607ed83cd9047b8c2796576bc83fa0de23a13a4dced07654b8ff137fe744047917"
|
||||||
:system-tags #{}}
|
:system-tags #{}}
|
||||||
{:alias "User A"
|
{:alias "User A"
|
||||||
:photo-path "photo2"
|
:identicon "photo2"
|
||||||
:public-key "0x048a2f8b80c60f89a91b4c1316e56f75b087f446e7b8701ceca06a40142d8efe1f5aa36bd0fee9e248060a8d5207b43ae98bef4617c18c71e66f920f324869c09f"}
|
:public-key "0x048a2f8b80c60f89a91b4c1316e56f75b087f446e7b8701ceca06a40142d8efe1f5aa36bd0fee9e248060a8d5207b43ae98bef4617c18c71e66f920f324869c09f"}
|
||||||
{:last-updated 0
|
{:last-updated 0
|
||||||
:name "User B"
|
:name "User B"
|
||||||
:photo-path "photo1"
|
:identicon "photo1"
|
||||||
:last-online 0
|
:last-online 0
|
||||||
:public-key "0x04985040682b77a32bb4bb58268a0719bd24ca4d07c255153fe1eb2ccd5883669627bd1a092d7cc76e8e4b9104327667b19dcda3ac469f572efabe588c38c1985f"
|
:public-key "0x04985040682b77a32bb4bb58268a0719bd24ca4d07c255153fe1eb2ccd5883669627bd1a092d7cc76e8e4b9104327667b19dcda3ac469f572efabe588c38c1985f"
|
||||||
:system-tags #{}}]))))))
|
:system-tags #{}}]))))))
|
||||||
|
@ -19,7 +19,6 @@
|
|||||||
#{}
|
#{}
|
||||||
%))
|
%))
|
||||||
(clojure.set/rename-keys {:id :public-key
|
(clojure.set/rename-keys {:id :public-key
|
||||||
:photoPath :photo-path
|
|
||||||
:tributeToTalk :tribute-to-talk
|
:tributeToTalk :tribute-to-talk
|
||||||
:ensVerifiedAt :ens-verified-at
|
:ensVerifiedAt :ens-verified-at
|
||||||
:ensVerified :ens-verified
|
:ensVerified :ens-verified
|
||||||
@ -38,7 +37,6 @@
|
|||||||
:ens-verified-at :ensVerifiedAt
|
:ens-verified-at :ensVerifiedAt
|
||||||
:last-ens-clock-value :lastENSClockValue
|
:last-ens-clock-value :lastENSClockValue
|
||||||
:ens-verification-retries :ensVerificationRetries
|
:ens-verification-retries :ensVerificationRetries
|
||||||
:photo-path :photoPath
|
|
||||||
:tribute-to-talk :tributeToTalk
|
:tribute-to-talk :tributeToTalk
|
||||||
:system-tags :systemTags
|
:system-tags :systemTags
|
||||||
:last-updated :lastUpdated
|
:last-updated :lastUpdated
|
||||||
|
@ -6,14 +6,14 @@
|
|||||||
(let [contact {:public-key "pk"
|
(let [contact {:public-key "pk"
|
||||||
:address "address"
|
:address "address"
|
||||||
:name "name"
|
:name "name"
|
||||||
:photo-path "photo-path"
|
:identicon "identicon"
|
||||||
:tribute-to-talk "tribute-to-talk"
|
:tribute-to-talk "tribute-to-talk"
|
||||||
:last-updated 1
|
:last-updated 1
|
||||||
:system-tags #{:a :b}}
|
:system-tags #{:a :b}}
|
||||||
expected-contact {:id "pk"
|
expected-contact {:id "pk"
|
||||||
:address "address"
|
:address "address"
|
||||||
:name "name"
|
:name "name"
|
||||||
:photoPath "photo-path"
|
:identicon "identicon"
|
||||||
:tributeToTalk "\"tribute-to-talk\""
|
:tributeToTalk "\"tribute-to-talk\""
|
||||||
|
|
||||||
:lastUpdated 1
|
:lastUpdated 1
|
||||||
@ -28,14 +28,14 @@
|
|||||||
(let [contact {:id "pk"
|
(let [contact {:id "pk"
|
||||||
:address "address"
|
:address "address"
|
||||||
:name "name"
|
:name "name"
|
||||||
:photoPath "photo-path"
|
:identicon "identicon"
|
||||||
:tributeToTalk "\"tribute-to-talk\""
|
:tributeToTalk "\"tribute-to-talk\""
|
||||||
:lastUpdated 1
|
:lastUpdated 1
|
||||||
:systemTags [":a" ":b"]}
|
:systemTags [":a" ":b"]}
|
||||||
expected-contact {:public-key "pk"
|
expected-contact {:public-key "pk"
|
||||||
:address "address"
|
:address "address"
|
||||||
:name "name"
|
:name "name"
|
||||||
:photo-path "photo-path"
|
:identicon "identicon"
|
||||||
:tribute-to-talk "tribute-to-talk"
|
:tribute-to-talk "tribute-to-talk"
|
||||||
|
|
||||||
:last-updated 1
|
:last-updated 1
|
||||||
|
@ -111,6 +111,10 @@
|
|||||||
"wakuext_getPushNotificationsServers" {}
|
"wakuext_getPushNotificationsServers" {}
|
||||||
"wakuext_enablePushNotificationsBlockMentions" {}
|
"wakuext_enablePushNotificationsBlockMentions" {}
|
||||||
"wakuext_disablePushNotificationsBlockMentions" {}
|
"wakuext_disablePushNotificationsBlockMentions" {}
|
||||||
|
"multiaccounts_getIdentityImages" {}
|
||||||
|
"multiaccounts_getIdentityImage" {}
|
||||||
|
"multiaccounts_storeIdentityImage" {}
|
||||||
|
"multiaccounts_deleteIdentityImage" {}
|
||||||
"status_chats" {}
|
"status_chats" {}
|
||||||
"localnotifications_switchWalletNotifications" {}
|
"localnotifications_switchWalletNotifications" {}
|
||||||
"localnotifications_notificationPreferences" {}
|
"localnotifications_notificationPreferences" {}
|
||||||
|
@ -139,14 +139,13 @@
|
|||||||
(handlers/register-handler-fx
|
(handlers/register-handler-fx
|
||||||
:multiaccounts.login.ui/multiaccount-selected
|
:multiaccounts.login.ui/multiaccount-selected
|
||||||
(fn [{:keys [db] :as cofx} [_ key-uid]]
|
(fn [{:keys [db] :as cofx} [_ key-uid]]
|
||||||
(let [{:keys [photo-path name public-key]}
|
(let [multiaccount (get-in db [:multiaccounts/multiaccounts key-uid])]
|
||||||
(get-in db [:multiaccounts/multiaccounts key-uid])]
|
|
||||||
(fx/merge
|
(fx/merge
|
||||||
cofx
|
cofx
|
||||||
{:db (-> db
|
{:db (-> db
|
||||||
(dissoc :intro-wizard)
|
(dissoc :intro-wizard)
|
||||||
(update :keycard dissoc :application-info))}
|
(update :keycard dissoc :application-info))}
|
||||||
(multiaccounts.login/open-login key-uid photo-path name public-key)))))
|
(multiaccounts.login/open-login multiaccount)))))
|
||||||
|
|
||||||
(handlers/register-handler-fx
|
(handlers/register-handler-fx
|
||||||
:login/filters-initialized
|
:login/filters-initialized
|
||||||
|
@ -27,9 +27,8 @@
|
|||||||
[cofx {:keys [logout?]}]
|
[cofx {:keys [logout?]}]
|
||||||
(let [{{:multiaccounts/keys [multiaccounts]} :db} cofx]
|
(let [{{:multiaccounts/keys [multiaccounts]} :db} cofx]
|
||||||
(when (and (seq multiaccounts) (not logout?))
|
(when (and (seq multiaccounts) (not logout?))
|
||||||
(let [{:keys [key-uid public-key photo-path name]}
|
(let [multiaccount (first (sort-by :timestamp > (vals multiaccounts)))]
|
||||||
(first (sort-by :timestamp > (vals multiaccounts)))]
|
(multiaccounts.login/open-login cofx multiaccount)))))
|
||||||
(multiaccounts.login/open-login cofx key-uid photo-path name public-key)))))
|
|
||||||
|
|
||||||
(fx/defn initialize-multiaccounts
|
(fx/defn initialize-multiaccounts
|
||||||
{:events [::initialize-multiaccounts]}
|
{:events [::initialize-multiaccounts]}
|
||||||
|
@ -311,11 +311,11 @@
|
|||||||
[{:keys [db] :as cofx} data]
|
[{:keys [db] :as cofx} data]
|
||||||
(let [{:keys [key-uid encryption-public-key whisper-private-key]
|
(let [{:keys [key-uid encryption-public-key whisper-private-key]
|
||||||
:as account-data} (js->clj data :keywordize-keys true)
|
:as account-data} (js->clj data :keywordize-keys true)
|
||||||
{:keys [photo-path name]} (get-in db [:multiaccounts/multiaccounts key-uid])
|
{:keys [identicon name]} (get-in db [:multiaccounts/multiaccounts key-uid])
|
||||||
key-uid (get-in db [:keycard :application-info :key-uid])
|
key-uid (get-in db [:keycard :application-info :key-uid])
|
||||||
multiaccount-data (types/clj->json {:name name
|
multiaccount-data (types/clj->json {:name name
|
||||||
:key-uid key-uid
|
:key-uid key-uid
|
||||||
:photo-path photo-path})
|
:identicon identicon})
|
||||||
save-keys? (get-in db [:multiaccounts/login :save-password?])]
|
save-keys? (get-in db [:multiaccounts/login :save-password?])]
|
||||||
(fx/merge cofx
|
(fx/merge cofx
|
||||||
{:db
|
{:db
|
||||||
@ -328,7 +328,7 @@
|
|||||||
(update :multiaccounts/login assoc
|
(update :multiaccounts/login assoc
|
||||||
:password encryption-public-key
|
:password encryption-public-key
|
||||||
:key-uid key-uid
|
:key-uid key-uid
|
||||||
:photo-path photo-path
|
:identicon identicon
|
||||||
:name name))
|
:name name))
|
||||||
|
|
||||||
:keycard/get-application-info {:pairing (get-pairing db key-uid)}
|
:keycard/get-application-info {:pairing (get-pairing db key-uid)}
|
||||||
|
@ -145,13 +145,13 @@
|
|||||||
[{:keys [db] :as cofx} key-uid [encryption-public-key whisper-private-key :as creds]]
|
[{:keys [db] :as cofx} key-uid [encryption-public-key whisper-private-key :as creds]]
|
||||||
(if (nil? creds)
|
(if (nil? creds)
|
||||||
(navigation/navigate-to-cofx cofx :keycard-login-pin nil)
|
(navigation/navigate-to-cofx cofx :keycard-login-pin nil)
|
||||||
(let [{:keys [photo-path name]} (get-in db [:multiaccounts/multiaccounts key-uid])
|
(let [{:keys [identicon name]} (get-in db [:multiaccounts/multiaccounts key-uid])
|
||||||
multiaccount-data (types/clj->json {:name name
|
multiaccount-data (types/clj->json {:name name
|
||||||
:key-uid key-uid
|
:key-uid key-uid
|
||||||
:photo-path photo-path})
|
:identicon identicon})
|
||||||
account-data {:key-uid key-uid
|
account-data {:key-uid key-uid
|
||||||
:encryption-public-key encryption-public-key
|
:encryption-public-key encryption-public-key
|
||||||
:whisper-private-key whisper-private-key}]
|
:whisper-private-key whisper-private-key}]
|
||||||
{:db
|
{:db
|
||||||
(-> db
|
(-> db
|
||||||
(assoc-in [:keycard :pin :status] nil)
|
(assoc-in [:keycard :pin :status] nil)
|
||||||
@ -162,7 +162,7 @@
|
|||||||
(update :multiaccounts/login assoc
|
(update :multiaccounts/login assoc
|
||||||
:password encryption-public-key
|
:password encryption-public-key
|
||||||
:key-uid key-uid
|
:key-uid key-uid
|
||||||
:photo-path photo-path
|
:identicon identicon
|
||||||
:name name
|
:name name
|
||||||
:save-password? true))
|
:save-password? true))
|
||||||
:keycard/login-with-keycard
|
:keycard/login-with-keycard
|
||||||
|
@ -137,7 +137,7 @@
|
|||||||
(let [{{:keys [multiaccount secrets flow]} :keycard} db
|
(let [{{:keys [multiaccount secrets flow]} :keycard} db
|
||||||
{:keys [address
|
{:keys [address
|
||||||
name
|
name
|
||||||
photo-path
|
identicon
|
||||||
public-key
|
public-key
|
||||||
whisper-public-key
|
whisper-public-key
|
||||||
wallet-public-key
|
wallet-public-key
|
||||||
@ -149,14 +149,14 @@
|
|||||||
encryption-public-key
|
encryption-public-key
|
||||||
instance-uid
|
instance-uid
|
||||||
key-uid
|
key-uid
|
||||||
recovered]} multiaccount
|
recovered]} multiaccount
|
||||||
{:keys [pairing paired-on]} secrets
|
{:keys [pairing paired-on]} secrets
|
||||||
{:keys [name photo-path]}
|
{:keys [name identicon]}
|
||||||
(if (nil? name)
|
(if (nil? name)
|
||||||
;; name might have been generated during recovery via passphrase
|
;; name might have been generated during recovery via passphrase
|
||||||
(get-in db [:intro-wizard :derived constants/path-whisper-keyword])
|
(get-in db [:intro-wizard :derived constants/path-whisper-keyword])
|
||||||
{:name name
|
{:name name
|
||||||
:photo-path photo-path})]
|
:identicon identicon})]
|
||||||
;; if a name is still `nil` we have to generate it before multiaccount's
|
;; if a name is still `nil` we have to generate it before multiaccount's
|
||||||
;; creation otherwise spec validation will fail
|
;; creation otherwise spec validation will fail
|
||||||
(if (nil? name)
|
(if (nil? name)
|
||||||
@ -176,7 +176,7 @@
|
|||||||
{:public-key whisper-public-key
|
{:public-key whisper-public-key
|
||||||
:address (eip55/address->checksum whisper-address)
|
:address (eip55/address->checksum whisper-address)
|
||||||
:name name
|
:name name
|
||||||
:photo-path photo-path}
|
:identicon identicon}
|
||||||
constants/path-default-wallet-keyword
|
constants/path-default-wallet-keyword
|
||||||
{:public-key wallet-public-key
|
{:public-key wallet-public-key
|
||||||
:address (eip55/address->checksum wallet-address)}}
|
:address (eip55/address->checksum wallet-address)}}
|
||||||
@ -264,7 +264,7 @@
|
|||||||
{:events [::on-name-and-photo-generated]
|
{:events [::on-name-and-photo-generated]
|
||||||
:interceptors [(re-frame/inject-cofx :random-guid-generator)
|
:interceptors [(re-frame/inject-cofx :random-guid-generator)
|
||||||
(re-frame/inject-cofx ::multiaccounts.create/get-signing-phrase)]}
|
(re-frame/inject-cofx ::multiaccounts.create/get-signing-phrase)]}
|
||||||
[{:keys [db] :as cofx} whisper-name photo-path]
|
[{:keys [db] :as cofx} whisper-name identicon]
|
||||||
(fx/merge
|
(fx/merge
|
||||||
cofx
|
cofx
|
||||||
{:db (update-in db [:keycard :multiaccount]
|
{:db (update-in db [:keycard :multiaccount]
|
||||||
@ -272,5 +272,5 @@
|
|||||||
(assoc multiacc
|
(assoc multiacc
|
||||||
:recovered true
|
:recovered true
|
||||||
:name whisper-name
|
:name whisper-name
|
||||||
:photo-path photo-path)))}
|
:identicon identicon)))}
|
||||||
(create-keycard-multiaccount)))
|
(create-keycard-multiaccount)))
|
||||||
|
@ -183,7 +183,7 @@
|
|||||||
(let [derived-data-extended
|
(let [derived-data-extended
|
||||||
(update derived-data
|
(update derived-data
|
||||||
constants/path-whisper-keyword
|
constants/path-whisper-keyword
|
||||||
merge {:name name :photo-path photo-path})]
|
merge {:name name :identicon photo-path})]
|
||||||
(reset! derived-acc
|
(reset! derived-acc
|
||||||
{:root-key root-data
|
{:root-key root-data
|
||||||
:derived derived-data-extended})))))))))))
|
:derived derived-data-extended})))))))))))
|
||||||
|
@ -2,7 +2,9 @@
|
|||||||
(:require [re-frame.core :as re-frame]
|
(:require [re-frame.core :as re-frame]
|
||||||
[status-im.ethereum.stateofus :as stateofus]
|
[status-im.ethereum.stateofus :as stateofus]
|
||||||
[status-im.multiaccounts.update.core :as multiaccounts.update]
|
[status-im.multiaccounts.update.core :as multiaccounts.update]
|
||||||
|
[status-im.ui.components.bottom-sheet.core :as bottom-sheet]
|
||||||
[status-im.native-module.core :as native-module]
|
[status-im.native-module.core :as native-module]
|
||||||
|
[status-im.ethereum.json-rpc :as json-rpc]
|
||||||
[status-im.utils.fx :as fx]
|
[status-im.utils.fx :as fx]
|
||||||
[status-im.utils.gfycat.core :as gfycat]
|
[status-im.utils.gfycat.core :as gfycat]
|
||||||
[status-im.utils.identicon :as identicon]
|
[status-im.utils.identicon :as identicon]
|
||||||
@ -10,6 +12,7 @@
|
|||||||
[status-im.theme.core :as theme]
|
[status-im.theme.core :as theme]
|
||||||
[status-im.utils.utils :as utils]
|
[status-im.utils.utils :as utils]
|
||||||
[quo.platform :as platform]
|
[quo.platform :as platform]
|
||||||
|
[taoensso.timbre :as log]
|
||||||
[clojure.string :as string]))
|
[clojure.string :as string]))
|
||||||
|
|
||||||
(defn contact-names
|
(defn contact-names
|
||||||
@ -54,12 +57,23 @@
|
|||||||
(str "@" (or username ens-name)))
|
(str "@" (or username ens-name)))
|
||||||
(or alias (gfycat/generate-gfy public-key)))))
|
(or alias (gfycat/generate-gfy public-key)))))
|
||||||
|
|
||||||
|
(def photo-quality-thumbnail :thumbnail)
|
||||||
|
(def photo-quality-large :large)
|
||||||
|
|
||||||
(defn displayed-photo
|
(defn displayed-photo
|
||||||
"If a photo-path is set use it, otherwise fallback on identicon or generate"
|
"If a photo, a image or an images array is set use it, otherwise fallback on identicon or generate"
|
||||||
[{:keys [photo-path identicon public-key]}]
|
[{:keys [images identicon public-key]}]
|
||||||
(or photo-path
|
(cond
|
||||||
identicon
|
(pos? (count images))
|
||||||
(identicon/identicon public-key)))
|
(:uri (or (photo-quality-thumbnail images)
|
||||||
|
(photo-quality-large images)
|
||||||
|
(first images)))
|
||||||
|
|
||||||
|
(not (string/blank? identicon))
|
||||||
|
identicon
|
||||||
|
|
||||||
|
:else
|
||||||
|
(identicon/identicon public-key)))
|
||||||
|
|
||||||
(re-frame/reg-fx
|
(re-frame/reg-fx
|
||||||
::chaos-mode-changed
|
::chaos-mode-changed
|
||||||
@ -145,3 +159,45 @@
|
|||||||
(fx/merge cofx
|
(fx/merge cofx
|
||||||
{::switch-theme theme}
|
{::switch-theme theme}
|
||||||
(multiaccounts.update/multiaccount-update :appearance theme {})))
|
(multiaccounts.update/multiaccount-update :appearance theme {})))
|
||||||
|
|
||||||
|
(defn clean-path [path]
|
||||||
|
(if path
|
||||||
|
(string/replace-first path #"file://" "")
|
||||||
|
(log/warn "[nativ-module] Empty path was provided")))
|
||||||
|
|
||||||
|
(fx/defn save-profile-picture
|
||||||
|
{:events [::save-profile-picture]}
|
||||||
|
[cofx path ax ay bx by]
|
||||||
|
(let [key-uid (get-in cofx [:db :multiaccount :key-uid])]
|
||||||
|
(fx/merge cofx
|
||||||
|
{::json-rpc/call [{:method "multiaccounts_storeIdentityImage"
|
||||||
|
:params [key-uid (clean-path path) ax ay bx by]
|
||||||
|
;; NOTE: In case of an error we can show a toast error
|
||||||
|
:on-success #(re-frame/dispatch [::update-local-picture %])}]}
|
||||||
|
(multiaccounts.update/optimistic :images [{:url path
|
||||||
|
:type (name photo-quality-large)}])
|
||||||
|
(bottom-sheet/hide-bottom-sheet))))
|
||||||
|
|
||||||
|
(fx/defn delete-profile-picture
|
||||||
|
{:events [::delete-profile-picture]}
|
||||||
|
[cofx name]
|
||||||
|
(let [key-uid (get-in cofx [:db :multiaccount :key-uid])]
|
||||||
|
(fx/merge cofx
|
||||||
|
{::json-rpc/call [{:method "multiaccounts_deleteIdentityImage"
|
||||||
|
:params [key-uid]
|
||||||
|
;; NOTE: In case of an error we could fallback to previous image in UI with a toast error
|
||||||
|
:on-success #(log/info "[multiaccount] Delete profile image" %)}]}
|
||||||
|
(multiaccounts.update/optimistic :images nil)
|
||||||
|
(bottom-sheet/hide-bottom-sheet))))
|
||||||
|
|
||||||
|
(fx/defn get-profile-picture
|
||||||
|
[cofx]
|
||||||
|
(let [key-uid (get-in cofx [:db :multiaccount :key-uid])]
|
||||||
|
{::json-rpc/call [{:method "multiaccounts_getIdentityImages"
|
||||||
|
:params [key-uid]
|
||||||
|
:on-success #(re-frame/dispatch [::update-local-picture %])}]}))
|
||||||
|
|
||||||
|
(fx/defn store-profile-picture
|
||||||
|
{:events [::update-local-picture]}
|
||||||
|
[cofx pics]
|
||||||
|
(multiaccounts.update/optimistic cofx :images pics))
|
||||||
|
@ -80,11 +80,11 @@
|
|||||||
public-key (get-in derived-data [constants/path-whisper-keyword :public-key])]
|
public-key (get-in derived-data [constants/path-whisper-keyword :public-key])]
|
||||||
(status/gfycat-identicon-async
|
(status/gfycat-identicon-async
|
||||||
public-key
|
public-key
|
||||||
(fn [name photo-path]
|
(fn [name identicon]
|
||||||
(let [derived-whisper (derived-data constants/path-whisper-keyword)
|
(let [derived-whisper (derived-data constants/path-whisper-keyword)
|
||||||
derived-data-extended (assoc-in derived-data
|
derived-data-extended (assoc-in derived-data
|
||||||
[constants/path-whisper-keyword]
|
[constants/path-whisper-keyword]
|
||||||
(merge derived-whisper {:name name :photo-path photo-path}))]
|
(merge derived-whisper {:name name :identicon identicon}))]
|
||||||
(re-frame/dispatch [::store-multiaccount-success
|
(re-frame/dispatch [::store-multiaccount-success
|
||||||
key-code derived-data-extended]))))))]
|
key-code derived-data-extended]))))))]
|
||||||
{::store-multiaccount [selected-id key-uid hashed-password callback]}))
|
{::store-multiaccount [selected-id key-uid hashed-password callback]}))
|
||||||
@ -192,12 +192,12 @@
|
|||||||
:wallet true
|
:wallet true
|
||||||
:path constants/path-default-wallet
|
:path constants/path-default-wallet
|
||||||
:name (i18n/label :t/ethereum-account)})
|
:name (i18n/label :t/ethereum-account)})
|
||||||
(let [{:keys [public-key address name photo-path]}
|
(let [{:keys [public-key address name identicon]}
|
||||||
(get-in multiaccount [:derived constants/path-whisper-keyword])]
|
(get-in multiaccount [:derived constants/path-whisper-keyword])]
|
||||||
{:public-key public-key
|
{:public-key public-key
|
||||||
:address (eip55/address->checksum address)
|
:address (eip55/address->checksum address)
|
||||||
:name name
|
:name name
|
||||||
:photo-path photo-path
|
:identicon identicon
|
||||||
:path constants/path-whisper
|
:path constants/path-whisper
|
||||||
:chat true})])
|
:chat true})])
|
||||||
|
|
||||||
@ -221,10 +221,10 @@
|
|||||||
:as multiaccount}
|
:as multiaccount}
|
||||||
password
|
password
|
||||||
{:keys [save-mnemonic? login?] :or {login? true save-mnemonic? false}}]
|
{:keys [save-mnemonic? login?] :or {login? true save-mnemonic? false}}]
|
||||||
(let [[wallet-account {:keys [public-key photo-path name]} :as accounts-data] (prepare-accounts-data multiaccount)
|
(let [[wallet-account {:keys [public-key identicon name]} :as accounts-data] (prepare-accounts-data multiaccount)
|
||||||
multiaccount-data {:name name
|
multiaccount-data {:name name
|
||||||
:address address
|
:address address
|
||||||
:photo-path photo-path
|
:identicon identicon
|
||||||
:key-uid key-uid
|
:key-uid key-uid
|
||||||
:keycard-pairing keycard-pairing}
|
:keycard-pairing keycard-pairing}
|
||||||
keycard-multiaccount? (boolean keycard-pairing)
|
keycard-multiaccount? (boolean keycard-pairing)
|
||||||
@ -243,7 +243,7 @@
|
|||||||
constants/path-wallet-root-keyword
|
constants/path-wallet-root-keyword
|
||||||
:address])
|
:address])
|
||||||
:name name
|
:name name
|
||||||
:photo-path photo-path
|
:identicon identicon
|
||||||
;; public key of the chat account
|
;; public key of the chat account
|
||||||
:public-key public-key
|
:public-key public-key
|
||||||
;; default address for Dapps
|
;; default address for Dapps
|
||||||
@ -269,7 +269,7 @@
|
|||||||
db (assoc db
|
db (assoc db
|
||||||
:multiaccounts/login {:key-uid key-uid
|
:multiaccounts/login {:key-uid key-uid
|
||||||
:name name
|
:name name
|
||||||
:photo-path photo-path
|
:identicon identicon
|
||||||
:password password
|
:password password
|
||||||
:creating? true
|
:creating? true
|
||||||
:processing true}
|
:processing true}
|
||||||
|
@ -19,7 +19,6 @@
|
|||||||
[status-im.ui.screens.mobile-network-settings.events :as mobile-network]
|
[status-im.ui.screens.mobile-network-settings.events :as mobile-network]
|
||||||
[status-im.navigation :as navigation]
|
[status-im.navigation :as navigation]
|
||||||
[status-im.utils.fx :as fx]
|
[status-im.utils.fx :as fx]
|
||||||
[status-im.utils.identicon :as identicon]
|
|
||||||
[status-im.utils.keychain.core :as keychain]
|
[status-im.utils.keychain.core :as keychain]
|
||||||
[status-im.utils.logging.core :as logging]
|
[status-im.utils.logging.core :as logging]
|
||||||
[status-im.utils.security :as security]
|
[status-im.utils.security :as security]
|
||||||
@ -76,7 +75,7 @@
|
|||||||
(fx/defn login
|
(fx/defn login
|
||||||
{:events [:multiaccounts.login.ui/password-input-submitted]}
|
{:events [:multiaccounts.login.ui/password-input-submitted]}
|
||||||
[{:keys [db]}]
|
[{:keys [db]}]
|
||||||
(let [{:keys [key-uid password name photo-path]} (:multiaccounts/login db)]
|
(let [{:keys [key-uid password name identicon]} (:multiaccounts/login db)]
|
||||||
{:db (-> db
|
{:db (-> db
|
||||||
(assoc-in [:multiaccounts/login :processing] true)
|
(assoc-in [:multiaccounts/login :processing] true)
|
||||||
(dissoc :intro-wizard)
|
(dissoc :intro-wizard)
|
||||||
@ -84,7 +83,7 @@
|
|||||||
::login [key-uid
|
::login [key-uid
|
||||||
(types/clj->json {:name name
|
(types/clj->json {:name name
|
||||||
:key-uid key-uid
|
:key-uid key-uid
|
||||||
:photo-path photo-path})
|
:identicon identicon})
|
||||||
(ethereum/sha3 (security/safe-unmask-data password))]}))
|
(ethereum/sha3 (security/safe-unmask-data password))]}))
|
||||||
|
|
||||||
(fx/defn finish-keycard-setup
|
(fx/defn finish-keycard-setup
|
||||||
@ -227,6 +226,7 @@
|
|||||||
(mobile-network/on-network-status-change)
|
(mobile-network/on-network-status-change)
|
||||||
(get-group-chat-invitations)
|
(get-group-chat-invitations)
|
||||||
(logging/set-log-level (:log-level multiaccount))
|
(logging/set-log-level (:log-level multiaccount))
|
||||||
|
(multiaccounts/get-profile-picture)
|
||||||
(multiaccounts/switch-preview-privacy-mode-flag)
|
(multiaccounts/switch-preview-privacy-mode-flag)
|
||||||
(link-preview/request-link-preview-whitelist))))
|
(link-preview/request-link-preview-whitelist))))
|
||||||
|
|
||||||
@ -337,19 +337,12 @@
|
|||||||
(navigation/navigate-to-cofx :tabs {:screen :chat-stack
|
(navigation/navigate-to-cofx :tabs {:screen :chat-stack
|
||||||
:params {:screen :home}})))))
|
:params {:screen :home}})))))
|
||||||
|
|
||||||
|
;; FIXME(Ferossgp): We should not copy keys as we denormalize the database,
|
||||||
|
;; this create desync between actual accounts and the one on login causing broken state
|
||||||
(fx/defn open-login
|
(fx/defn open-login
|
||||||
[{:keys [db] :as cofx} key-uid photo-path name public-key]
|
[{:keys [db] :as cofx} {:keys [key-uid] :as multiaccount}]
|
||||||
(fx/merge cofx
|
(fx/merge cofx
|
||||||
{:db (-> db
|
{:db (assoc db :multiaccounts/login multiaccount)}
|
||||||
(update :multiaccounts/login assoc
|
|
||||||
:public-key public-key
|
|
||||||
:key-uid key-uid
|
|
||||||
:photo-path photo-path
|
|
||||||
:name name)
|
|
||||||
(assoc :profile/photo-added? (= (identicon/identicon public-key) photo-path))
|
|
||||||
(update :multiaccounts/login dissoc
|
|
||||||
:error
|
|
||||||
:password))}
|
|
||||||
(keychain/get-auth-method key-uid)))
|
(keychain/get-auth-method key-uid)))
|
||||||
|
|
||||||
(fx/defn open-login-callback
|
(fx/defn open-login-callback
|
||||||
|
@ -5,14 +5,14 @@
|
|||||||
:tags #{}
|
:tags #{}
|
||||||
:address "2f88d65f3cb52605a54a833ae118fb1363acccd2"
|
:address "2f88d65f3cb52605a54a833ae118fb1363acccd2"
|
||||||
:name "Darkviolet Lightgreen Halcyon"
|
:name "Darkviolet Lightgreen Halcyon"
|
||||||
:photo-path "data:image/png;base64iVBORw0KGgoAAAANSUhEUgAAACgAAAAoCAMAAAC7IEhfAAADAFBMVEX///+M2KwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADdPOdBAAABAHRSTlP//wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKmfXxgAABnNJREFUeNoBaAaX+QAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAY5UBARL8TK8AAAAASUVORK5CYII="
|
:identicon "data:image/png;base64iVBORw0KGgoAAAANSUhEUgAAACgAAAAoCAMAAAC7IEhfAAADAFBMVEX///+M2KwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADdPOdBAAABAHRSTlP//wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKmfXxgAABnNJREFUeNoBaAaX+QAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAY5UBARL8TK8AAAAASUVORK5CYII="
|
||||||
:system-tags #{:contact/added}
|
:system-tags #{:contact/added}
|
||||||
:last-online 0
|
:last-online 0
|
||||||
:public-key "0x04d6e56a475cd35f512d6ce0bf76c2c2af435c85ff48c2b9bdefd129f620e051a436f50961eae5717b2a750e59c3f5b60647d927da46d0b8b11621640b5678fc24"}
|
:public-key "0x04d6e56a475cd35f512d6ce0bf76c2c2af435c85ff48c2b9bdefd129f620e051a436f50961eae5717b2a750e59c3f5b60647d927da46d0b8b11621640b5678fc24"}
|
||||||
{:last-updated 1547271764000
|
{:last-updated 1547271764000
|
||||||
:address "b267ff8336ac10b3a1986c04a70ff91fb03d0b78"
|
:address "b267ff8336ac10b3a1986c04a70ff91fb03d0b78"
|
||||||
:name "rv"
|
:name "rv"
|
||||||
:photo-path "data:image/png;base64iVBORw0KGgoAAAANSUhEUgAAACgAAAAoCAMAAAC7IEhfAAADAFBMVEX////VjNgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAwYzy6AAABAHRSTlP//wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKmfXxgAABnNJREFUeNoBaAaX+QAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAAAAAAEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEAAAAAAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQAAAAABAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAAAAAAEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA6IYA4bRtf+EAAAAASUVORK5CYII="
|
:identicon "data:image/png;base64iVBORw0KGgoAAAANSUhEUgAAACgAAAAoCAMAAAC7IEhfAAADAFBMVEX////VjNgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAwYzy6AAABAHRSTlP//wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKmfXxgAABnNJREFUeNoBaAaX+QAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEBAQEBAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQEBAQEBAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAQEBAQEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAAAAAAEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEAAAAAAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQAAAAABAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAAAAAAEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA6IYA4bRtf+EAAAAASUVORK5CYII="
|
||||||
:system-tags #{:contact/added}
|
:system-tags #{:contact/added}
|
||||||
:last-online 0
|
:last-online 0
|
||||||
:public-key "0x043ae31038ff45a31b096a91d3f8290e079366fbbae76a00fbbd349cd0e5b8d7598965d206772ec4504f68908649a08383cdc51a52cdae5e9ccc744ace4d37020f"}])
|
:public-key "0x043ae31038ff45a31b096a91d3f8290e079366fbbae76a00fbbd349cd0e5b8d7598965d206772ec4504f68908649a08383cdc51a52cdae5e9ccc744ace4d37020f"}])
|
||||||
@ -96,7 +96,7 @@
|
|||||||
:poa #{}}
|
:poa #{}}
|
||||||
:preview-privacy? true
|
:preview-privacy? true
|
||||||
:fleet :eth.prod
|
:fleet :eth.prod
|
||||||
:photo-path "data:image/png;base64iVBORw0KGgoAAAANSUhEUgAAACgAAAAoCAMAAAC7IEhfAAADAFBMVEX////YsYwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABPGFwxAAABAHRSTlP//wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKmfXxgAABnNJREFUeNoBaAaX+QAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAQEBAQAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAQEBAQAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAQEBAQAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAQEBAQAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAAAAAAEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEAAAAAAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQAAAAABAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAAAAAAEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAloYA4a9rBHIAAAAASUVORK5CYII="
|
:identicon "data:image/png;base64iVBORw0KGgoAAAANSUhEUgAAACgAAAAoCAMAAAC7IEhfAAADAFBMVEX////YsYwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABPGFwxAAABAHRSTlP//wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKmfXxgAABnNJREFUeNoBaAaX+QAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAQEBAQAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAQEBAQAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAQEBAQAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEAAAAAAQEBAQAAAAABAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQAAAAABAQEBAAAAAAEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAAAAAAEBAQEAAAAAAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAAAAAAEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQEBAQEBAQEAAAAAAQEBAQEBAQEAAAAAAAAAAAAAAAAAAAAAAAAAAAABAQEBAQEBAQAAAAABAQEBAQEBAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAEBAQEBAQEBAAAAAAEBAQEBAQEBAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAloYA4a9rBHIAAAAASUVORK5CYII="
|
||||||
:wallet-set-up-passed? false
|
:wallet-set-up-passed? false
|
||||||
:public-key "0x04173f7cdea0076a7998abb674cc79fe61337c42db77043c01d5b0f3e3ac1e5a45bca0c93bb9f3c3d38b7cc9a7337cd64f9f9b2114fe4bbdfe1ae2633ba14d8c9c"
|
:public-key "0x04173f7cdea0076a7998abb674cc79fe61337c42db77043c01d5b0f3e3ac1e5a45bca0c93bb9f3c3d38b7cc9a7337cd64f9f9b2114fe4bbdfe1ae2633ba14d8c9c"
|
||||||
:keycard-key-uid nil
|
:keycard-key-uid nil
|
||||||
|
@ -14,11 +14,11 @@
|
|||||||
(let [cofx {:db {:multiaccounts/login {:key-uid "key-uid"
|
(let [cofx {:db {:multiaccounts/login {:key-uid "key-uid"
|
||||||
:password "password"
|
:password "password"
|
||||||
:name "user"
|
:name "user"
|
||||||
:photo-path "photo"}}}
|
:identicon "photo"}}}
|
||||||
efx (login.core/login cofx)]
|
efx (login.core/login cofx)]
|
||||||
(testing "Change multiaccount."
|
(testing "Change multiaccount."
|
||||||
(is (= (::login.core/login efx)
|
(is (= (::login.core/login efx)
|
||||||
["key-uid" "{\"name\":\"user\",\"key-uid\":\"key-uid\",\"photo-path\":\"photo\"}" (ethereum/sha3 "password")])))
|
["key-uid" "{\"name\":\"user\",\"key-uid\":\"key-uid\",\"identicon\":\"photo\"}" (ethereum/sha3 "password")])))
|
||||||
(testing "start activity indicator"
|
(testing "start activity indicator"
|
||||||
(is (= (get-in efx [:db :multiaccounts/login :processing]) true))))))
|
(is (= (get-in efx [:db :multiaccounts/login :processing]) true))))))
|
||||||
|
|
||||||
|
@ -108,11 +108,11 @@
|
|||||||
public-key (get-in derived-data [constants/path-whisper-keyword :public-key])]
|
public-key (get-in derived-data [constants/path-whisper-keyword :public-key])]
|
||||||
(status/gfycat-identicon-async
|
(status/gfycat-identicon-async
|
||||||
public-key
|
public-key
|
||||||
(fn [name photo-path]
|
(fn [name identicon]
|
||||||
(let [derived-data-extended
|
(let [derived-data-extended
|
||||||
(update derived-data
|
(update derived-data
|
||||||
constants/path-whisper-keyword
|
constants/path-whisper-keyword
|
||||||
merge {:name name :photo-path photo-path})]
|
merge {:name name :identicon identicon})]
|
||||||
(re-frame/dispatch [::import-multiaccount-success
|
(re-frame/dispatch [::import-multiaccount-success
|
||||||
root-data derived-data-extended]))))))))))))
|
root-data derived-data-extended]))))))))))))
|
||||||
|
|
||||||
|
@ -5,9 +5,9 @@
|
|||||||
|
|
||||||
(fx/defn send-multiaccount-update [{:keys [db] :as cofx}]
|
(fx/defn send-multiaccount-update [{:keys [db] :as cofx}]
|
||||||
(let [multiaccount (:multiaccount db)
|
(let [multiaccount (:multiaccount db)
|
||||||
{:keys [name preferred-name photo-path address]} multiaccount]
|
{:keys [name preferred-name address]} multiaccount]
|
||||||
{::json-rpc/call [{:method (json-rpc/call-ext-method "sendContactUpdates")
|
{::json-rpc/call [{:method (json-rpc/call-ext-method "sendContactUpdates")
|
||||||
:params [(or preferred-name name) photo-path]
|
:params [(or preferred-name name) ""]
|
||||||
:on-success #(log/debug "sent contact update")}]}))
|
:on-success #(log/debug "sent contact update")}]}))
|
||||||
|
|
||||||
(fx/defn multiaccount-update
|
(fx/defn multiaccount-update
|
||||||
@ -30,7 +30,7 @@
|
|||||||
:params [setting setting-value]
|
:params [setting setting-value]
|
||||||
:on-success on-success}]}
|
:on-success on-success}]}
|
||||||
(when (and (not dont-sync?)
|
(when (and (not dont-sync?)
|
||||||
(#{:name :photo-path :prefered-name} setting))
|
(#{:name :prefered-name} setting))
|
||||||
(send-multiaccount-update))))))
|
(send-multiaccount-update))))))
|
||||||
|
|
||||||
(fx/defn clean-seed-phrase
|
(fx/defn clean-seed-phrase
|
||||||
|
@ -1,29 +0,0 @@
|
|||||||
(ns status-im.multiaccounts.update.publisher
|
|
||||||
(:require [re-frame.core :as re-frame]
|
|
||||||
[status-im.ethereum.json-rpc :as json-rpc]
|
|
||||||
[taoensso.timbre :as log]))
|
|
||||||
|
|
||||||
;; Publish updates every 48 hours
|
|
||||||
(def publish-updates-interval (* 48 60 60 1000))
|
|
||||||
|
|
||||||
(defn publish-update! [{:keys [db now]}]
|
|
||||||
(let [peers-count (:peers-count db)
|
|
||||||
last-updated (get-in
|
|
||||||
db
|
|
||||||
[:multiaccount :last-updated])]
|
|
||||||
(when (and (pos? peers-count)
|
|
||||||
(pos? last-updated)
|
|
||||||
(< publish-updates-interval
|
|
||||||
(- now last-updated)))
|
|
||||||
(let [multiaccount (:multiaccount db)
|
|
||||||
{:keys [name preferred-name photo-path]} multiaccount]
|
|
||||||
|
|
||||||
(log/debug "sending contact updates")
|
|
||||||
(json-rpc/call {:method (json-rpc/call-ext-method "sendContactUpdates")
|
|
||||||
:params [(or preferred-name name) photo-path]
|
|
||||||
:on-failure #(do
|
|
||||||
(log/warn "failed to send contact updates")
|
|
||||||
(re-frame/dispatch [:multiaccounts.update.callback/failed-to-publish]))
|
|
||||||
:on-success #(do
|
|
||||||
(log/debug "sent contact updates")
|
|
||||||
(re-frame/dispatch [:multiaccounts.update.callback/published]))})))))
|
|
@ -171,9 +171,9 @@
|
|||||||
|
|
||||||
(defn send-installation-messages [{:keys [db]}]
|
(defn send-installation-messages [{:keys [db]}]
|
||||||
(let [multiaccount (:multiaccount db)
|
(let [multiaccount (:multiaccount db)
|
||||||
{:keys [name preferred-name photo-path]} multiaccount]
|
{:keys [name preferred-name identicon]} multiaccount]
|
||||||
{::json-rpc/call [{:method (json-rpc/call-ext-method "syncDevices")
|
{::json-rpc/call [{:method (json-rpc/call-ext-method "syncDevices")
|
||||||
:params [(or preferred-name name) photo-path]
|
:params [(or preferred-name name) identicon]
|
||||||
:on-success #(log/debug "successfully synced devices")}]}))
|
:on-success #(log/debug "successfully synced devices")}]}))
|
||||||
|
|
||||||
(defn installation<-rpc [{:keys [metadata id enabled]}]
|
(defn installation<-rpc [{:keys [metadata id enabled]}]
|
||||||
|
@ -99,7 +99,6 @@
|
|||||||
(reg-root-key-sub :my-profile/advanced? :my-profile/advanced?)
|
(reg-root-key-sub :my-profile/advanced? :my-profile/advanced?)
|
||||||
(reg-root-key-sub :my-profile/editing? :my-profile/editing?)
|
(reg-root-key-sub :my-profile/editing? :my-profile/editing?)
|
||||||
(reg-root-key-sub :my-profile/profile :my-profile/profile)
|
(reg-root-key-sub :my-profile/profile :my-profile/profile)
|
||||||
(reg-root-key-sub :profile/photo-added? :profile/photo-added?)
|
|
||||||
|
|
||||||
;;multiaccount
|
;;multiaccount
|
||||||
(reg-root-key-sub :multiaccounts/multiaccounts :multiaccounts/multiaccounts)
|
(reg-root-key-sub :multiaccounts/multiaccounts :multiaccounts/multiaccounts)
|
||||||
@ -275,9 +274,9 @@
|
|||||||
:intro-wizard/recovery-success
|
:intro-wizard/recovery-success
|
||||||
:<- [:intro-wizard]
|
:<- [:intro-wizard]
|
||||||
(fn [wizard-state]
|
(fn [wizard-state]
|
||||||
{:pubkey (get-in wizard-state [:derived constants/path-whisper-keyword :public-key])
|
{:pubkey (get-in wizard-state [:derived constants/path-whisper-keyword :public-key])
|
||||||
:name (get-in wizard-state [:derived constants/path-whisper-keyword :name])
|
:name (get-in wizard-state [:derived constants/path-whisper-keyword :name])
|
||||||
:photo-path (get-in wizard-state [:derived constants/path-whisper-keyword :photo-path])
|
:identicon (get-in wizard-state [:derived constants/path-whisper-keyword :identicon])
|
||||||
:processing? (:processing? wizard-state)}))
|
:processing? (:processing? wizard-state)}))
|
||||||
|
|
||||||
(re-frame/reg-sub
|
(re-frame/reg-sub
|
||||||
@ -477,7 +476,7 @@
|
|||||||
(fn [current-account]
|
(fn [current-account]
|
||||||
(some->
|
(some->
|
||||||
current-account
|
current-account
|
||||||
(select-keys [:name :preferred-name :public-key :photo-path])
|
(select-keys [:name :preferred-name :public-key :identicon :image :images])
|
||||||
(clojure.set/rename-keys {:name :alias})
|
(clojure.set/rename-keys {:name :alias})
|
||||||
(multiaccounts/contact-with-names))))
|
(multiaccounts/contact-with-names))))
|
||||||
|
|
||||||
@ -811,13 +810,16 @@
|
|||||||
|
|
||||||
(re-frame/reg-sub
|
(re-frame/reg-sub
|
||||||
:chats/photo-path
|
:chats/photo-path
|
||||||
:<- [:contacts/contacts]
|
:<- [::contacts]
|
||||||
:<- [:multiaccount]
|
:<- [:multiaccount]
|
||||||
(fn [[contacts multiaccount] [_ id]]
|
(fn [[contacts multiaccount] [_ id identicon]]
|
||||||
(multiaccounts/displayed-photo (or (get contacts id)
|
(let [contact (or (get contacts id)
|
||||||
(when (= id (:public-key multiaccount))
|
(when (= id (:public-key multiaccount)
|
||||||
multiaccount)
|
multiaccount))
|
||||||
(contact.db/public-key->new-contact id)))))
|
(if identicon
|
||||||
|
{:identicon identicon}
|
||||||
|
(contact.db/public-key->new-contact id)))]
|
||||||
|
(multiaccounts/displayed-photo contact))))
|
||||||
|
|
||||||
(re-frame/reg-sub
|
(re-frame/reg-sub
|
||||||
:chats/unread-messages-number
|
:chats/unread-messages-number
|
||||||
@ -935,10 +937,13 @@
|
|||||||
:<- [:contacts/contacts]
|
:<- [:contacts/contacts]
|
||||||
(fn [contacts]
|
(fn [contacts]
|
||||||
(reduce
|
(reduce
|
||||||
(fn [acc [key {:keys [alias name identicon public-key nickname] :as contact}]]
|
(fn [acc [key {:keys [alias name added? blocked? identicon public-key nickname]}]]
|
||||||
(if (and alias
|
(if (and alias
|
||||||
(not= alias "")
|
(not= alias "")
|
||||||
(not (contact.db/blocked? contact)))
|
(or name
|
||||||
|
nickname
|
||||||
|
added?)
|
||||||
|
(not blocked?))
|
||||||
(let [name (utils/safe-replace name ".stateofus.eth" "")]
|
(let [name (utils/safe-replace name ".stateofus.eth" "")]
|
||||||
(assoc acc public-key
|
(assoc acc public-key
|
||||||
(mentions/add-searchable-phrases
|
(mentions/add-searchable-phrases
|
||||||
@ -957,14 +962,13 @@
|
|||||||
:<- [:chats/mentionable-contacts]
|
:<- [:chats/mentionable-contacts]
|
||||||
:<- [:contacts/blocked-set]
|
:<- [:contacts/blocked-set]
|
||||||
:<- [:multiaccount]
|
:<- [:multiaccount]
|
||||||
(fn [[{:keys [users]} contacts blocked {:keys [name preferred-name photo-path public-key]}]]
|
(fn [[{:keys [users]} contacts blocked {:keys [name preferred-name public-key]}]]
|
||||||
(apply dissoc
|
(apply dissoc
|
||||||
(-> users
|
(-> users
|
||||||
(merge contacts)
|
(merge contacts)
|
||||||
(assoc public-key (mentions/add-searchable-phrases
|
(assoc public-key (mentions/add-searchable-phrases
|
||||||
{:alias name
|
{:alias name
|
||||||
:name (or preferred-name name)
|
:name (or preferred-name name)
|
||||||
:identicon photo-path
|
|
||||||
:public-key public-key})))
|
:public-key public-key})))
|
||||||
blocked)))
|
blocked)))
|
||||||
|
|
||||||
@ -1844,8 +1848,11 @@
|
|||||||
(re-frame/reg-sub
|
(re-frame/reg-sub
|
||||||
:contacts/contact-by-address
|
:contacts/contact-by-address
|
||||||
:<- [:contacts/contacts]
|
:<- [:contacts/contacts]
|
||||||
(fn [contacts [_ address]]
|
:<- [:multiaccount/contact]
|
||||||
(contact.db/find-contact-by-address contacts address)))
|
(fn [[contacts multiaccount] [_ address]]
|
||||||
|
(if (ethereum/address= address (:public-key multiaccount))
|
||||||
|
multiaccount
|
||||||
|
(contact.db/find-contact-by-address contacts address))))
|
||||||
|
|
||||||
(re-frame/reg-sub
|
(re-frame/reg-sub
|
||||||
:contacts/contacts-by-address
|
:contacts/contacts-by-address
|
||||||
@ -2416,3 +2423,9 @@
|
|||||||
(first (filter #(notifications/preference= % {:service "wallet"
|
(first (filter #(notifications/preference= % {:service "wallet"
|
||||||
:event "transaction"
|
:event "transaction"
|
||||||
:identifier "all"}) pref))))
|
:identifier "all"}) pref))))
|
||||||
|
|
||||||
|
(re-frame/reg-sub
|
||||||
|
:profile/has-picture
|
||||||
|
:<- [:multiaccount]
|
||||||
|
(fn [multiaccount]
|
||||||
|
(pos? (count (get multiaccount :images)))))
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
(:require [clojure.string :as string]
|
(:require [clojure.string :as string]
|
||||||
[re-frame.core :as re-frame.core]
|
[re-frame.core :as re-frame.core]
|
||||||
[status-im.multiaccounts.core :as multiaccounts]
|
[status-im.multiaccounts.core :as multiaccounts]
|
||||||
|
[status-im.ui.components.icons.vector-icons :as icons]
|
||||||
[status-im.ui.components.chat-icon.styles :as styles]
|
[status-im.ui.components.chat-icon.styles :as styles]
|
||||||
[status-im.ui.components.colors :as colors]
|
[status-im.ui.components.colors :as colors]
|
||||||
[status-im.ui.components.react :as react]
|
[status-im.ui.components.react :as react]
|
||||||
@ -125,11 +126,9 @@
|
|||||||
:default-chat-icon (styles/default-chat-icon-profile color size)
|
:default-chat-icon (styles/default-chat-icon-profile color size)
|
||||||
:default-chat-icon-text (styles/default-chat-icon-text size)} override-styles)]
|
:default-chat-icon-text (styles/default-chat-icon-text size)} override-styles)]
|
||||||
[react/view (:container styles)
|
[react/view (:container styles)
|
||||||
(when edit?
|
|
||||||
[react/view (styles/profile-icon-mask size)])
|
|
||||||
(when edit?
|
|
||||||
[react/view (styles/profile-icon-edit-text-containter size)
|
|
||||||
[react/i18n-text {:style styles/profile-icon-edit-text :key :edit}]])
|
|
||||||
(if (and photo-path (seq photo-path))
|
(if (and photo-path (seq photo-path))
|
||||||
[photos/photo photo-path styles]
|
[photos/photo photo-path styles]
|
||||||
[default-chat-icon name styles])]))
|
[default-chat-icon name styles])
|
||||||
|
(when edit?
|
||||||
|
[react/view {:style (styles/chat-icon-profile-edit)}
|
||||||
|
[icons/tiny-icon :tiny-icons/tiny-edit {:color colors/white-persist}]])]))
|
||||||
|
@ -121,23 +121,15 @@
|
|||||||
{:width 36
|
{:width 36
|
||||||
:height 36})
|
:height 36})
|
||||||
|
|
||||||
(defn profile-icon-mask [size]
|
(defn chat-icon-profile-edit []
|
||||||
{:height size
|
{:width 24
|
||||||
:width size
|
:height 24
|
||||||
|
:border-radius 12
|
||||||
|
:border-width 1
|
||||||
|
:border-color colors/white-persist
|
||||||
|
:background-color colors/blue
|
||||||
|
:justify-content :center
|
||||||
|
:align-items :center
|
||||||
:position :absolute
|
:position :absolute
|
||||||
:z-index 1
|
:bottom -2
|
||||||
:background-color colors/black
|
:right -2})
|
||||||
:opacity 0.4
|
|
||||||
:border-radius 50})
|
|
||||||
|
|
||||||
(defn profile-icon-edit-text-containter [size]
|
|
||||||
{:height size
|
|
||||||
:width size
|
|
||||||
:position :absolute
|
|
||||||
:z-index 2
|
|
||||||
:align-items :center
|
|
||||||
:justify-content :center})
|
|
||||||
|
|
||||||
(def profile-icon-edit-text
|
|
||||||
{:color colors/white
|
|
||||||
:background-color :transparent})
|
|
||||||
|
@ -37,23 +37,27 @@
|
|||||||
(when-not minimized
|
(when-not minimized
|
||||||
{:padding-top subtitle-margin})))
|
{:padding-top subtitle-margin})))
|
||||||
|
|
||||||
(defn extended-header [{:keys [title photo color subtitle subtitle-icon on-press monospace bottom-separator]
|
(defn extended-header [{:keys [title photo color subtitle subtitle-icon on-edit on-press monospace bottom-separator]
|
||||||
:or {bottom-separator true}}]
|
:or {bottom-separator true}}]
|
||||||
(fn [{:keys [animation minimized]}]
|
(fn [{:keys [animation minimized]}]
|
||||||
(let [wrapper (if on-press
|
(let [wrapper (if on-press
|
||||||
[rn/touchable-opacity {:on-press on-press}]
|
[rn/touchable-opacity {:on-press on-press}]
|
||||||
[:<>])]
|
[:<>])
|
||||||
|
editable (if (and (not minimized) on-edit)
|
||||||
|
[rn/touchable-opacity {:on-press on-edit}]
|
||||||
|
[:<>])]
|
||||||
(into
|
(into
|
||||||
wrapper
|
wrapper
|
||||||
[[animated/view {:pointer-events :box-none}
|
[[animated/view {:pointer-events :box-none}
|
||||||
[animated/view {:style (container-style {:animation animation
|
[animated/view {:style (container-style {:animation animation
|
||||||
:minimized minimized})
|
:minimized minimized})
|
||||||
:pointer-events :box-none}
|
:pointer-events :box-none}
|
||||||
[animated/view {:pointer-events :box-none}
|
(into editable
|
||||||
[chat-icon.screen/profile-icon-view
|
[[animated/view {:pointer-events :box-none}
|
||||||
photo title color nil
|
[chat-icon.screen/profile-icon-view
|
||||||
(if minimized avatar-minimized-size avatar-extended-size)
|
photo title color (and (not minimized) on-edit)
|
||||||
nil]]
|
(if minimized avatar-minimized-size avatar-extended-size)
|
||||||
|
nil]]])
|
||||||
[animated/view {:style (header-text)
|
[animated/view {:style (header-text)
|
||||||
:pointer-events :box-none}
|
:pointer-events :box-none}
|
||||||
[quo/text {:animated? true
|
[quo/text {:animated? true
|
||||||
|
@ -194,9 +194,12 @@
|
|||||||
(defn show-image-picker
|
(defn show-image-picker
|
||||||
([images-fn]
|
([images-fn]
|
||||||
(show-image-picker images-fn nil))
|
(show-image-picker images-fn nil))
|
||||||
([images-fn {:keys [multiple media-type]}]
|
([images-fn {:keys [media-type]
|
||||||
|
:or {media-type "any"}
|
||||||
|
:as props}]
|
||||||
(-> ^js image-picker
|
(-> ^js image-picker
|
||||||
(.openPicker (clj->js {:multiple multiple :mediaType (or media-type "any")}))
|
(.openPicker (clj->js (merge {:mediaType media-type}
|
||||||
|
props)))
|
||||||
(.then images-fn)
|
(.then images-fn)
|
||||||
(.catch show-access-error))))
|
(.catch show-access-error))))
|
||||||
|
|
||||||
|
@ -18,7 +18,7 @@
|
|||||||
[status-im.chat.models.mentions :as mentions]
|
[status-im.chat.models.mentions :as mentions]
|
||||||
[status-im.ui.components.list.views :as list]
|
[status-im.ui.components.list.views :as list]
|
||||||
[quo.components.list.item :as list-item]
|
[quo.components.list.item :as list-item]
|
||||||
[status-im.ui.screens.chat.styles.photos :as photo-style]
|
[status-im.ui.screens.chat.photos :as photos]
|
||||||
[reagent.core :as reagent]))
|
[reagent.core :as reagent]))
|
||||||
|
|
||||||
(def panel->icons {:extensions :main-icons/commands
|
(def panel->icons {:extensions :main-icons/commands
|
||||||
@ -199,18 +199,10 @@
|
|||||||
input-with-mentions)]]))
|
input-with-mentions)]]))
|
||||||
|
|
||||||
(defn mention-item
|
(defn mention-item
|
||||||
[[_ {:keys [identicon alias name nickname] :as user}] _ _ text-input-ref]
|
[[public-key {:keys [alias name nickname] :as user}] _ _ text-input-ref]
|
||||||
(let [ens-name? (not= alias name)]
|
(let [ens-name? (not= alias name)]
|
||||||
[list-item/list-item
|
[list-item/list-item
|
||||||
(cond-> {:icon
|
(cond-> {:icon [photos/member-photo public-key]
|
||||||
[rn/view {:style {}}
|
|
||||||
[rn/image
|
|
||||||
{:source {:uri identicon}
|
|
||||||
:style (photo-style/photo-border
|
|
||||||
photo-style/default-size
|
|
||||||
nil)
|
|
||||||
:resize-mode :cover}]]
|
|
||||||
:icon-container-style {}
|
|
||||||
:size :small
|
:size :small
|
||||||
:text-size :small
|
:text-size :small
|
||||||
:title
|
:title
|
||||||
|
@ -211,7 +211,8 @@
|
|||||||
|
|
||||||
(defn message-content-wrapper
|
(defn message-content-wrapper
|
||||||
"Author, userpic and delivery wrapper"
|
"Author, userpic and delivery wrapper"
|
||||||
[{:keys [first-in-group? display-photo? identicon display-username?
|
[{:keys [first-in-group? display-photo? display-username?
|
||||||
|
identicon
|
||||||
from outgoing]
|
from outgoing]
|
||||||
:as message} content {:keys [modal close-modal]}]
|
:as message} content {:keys [modal close-modal]}]
|
||||||
[react/view {:style (style/message-wrapper message)
|
[react/view {:style (style/message-wrapper message)
|
||||||
@ -224,7 +225,7 @@
|
|||||||
(when first-in-group?
|
(when first-in-group?
|
||||||
[react/touchable-highlight {:on-press #(do (when modal (close-modal))
|
[react/touchable-highlight {:on-press #(do (when modal (close-modal))
|
||||||
(re-frame/dispatch [:chat.ui/show-profile-without-adding-contact from]))}
|
(re-frame/dispatch [:chat.ui/show-profile-without-adding-contact from]))}
|
||||||
[photos/member-identicon identicon]])])
|
[photos/member-photo from identicon]])])
|
||||||
[react/view {:style (style/message-author-wrapper outgoing display-photo?)}
|
[react/view {:style (style/message-author-wrapper outgoing display-photo?)}
|
||||||
(when display-username?
|
(when display-username?
|
||||||
[react/touchable-opacity {:style style/message-author-touchable
|
[react/touchable-opacity {:style style/message-author-touchable
|
||||||
|
@ -1,9 +1,10 @@
|
|||||||
(ns status-im.ui.screens.chat.photos
|
(ns status-im.ui.screens.chat.photos
|
||||||
(:require [status-im.ui.components.react :as react]
|
(:require [re-frame.core :as re-frame]
|
||||||
|
[status-im.ui.components.react :as react]
|
||||||
[status-im.ui.screens.chat.styles.photos :as style]
|
[status-im.ui.screens.chat.styles.photos :as style]
|
||||||
[status-im.ui.screens.profile.db :as profile.db]
|
[status-im.ui.screens.profile.db :as profile.db]
|
||||||
[status-im.utils.image :as utils.image])
|
[status-im.multiaccounts.core :as multiaccounts]
|
||||||
(:require-macros [status-im.utils.views :refer [defview letsubs]]))
|
[status-im.utils.image :as utils.image]))
|
||||||
|
|
||||||
(defn photo [photo-path {:keys [size accessibility-label]}]
|
(defn photo [photo-path {:keys [size accessibility-label]}]
|
||||||
(let [identicon? (when photo-path (profile.db/base64-png? photo-path))]
|
(let [identicon? (when photo-path (profile.db/base64-png? photo-path))]
|
||||||
@ -15,11 +16,16 @@
|
|||||||
(when identicon?
|
(when identicon?
|
||||||
[react/view {:style (style/photo-border size)}])]))
|
[react/view {:style (style/photo-border size)}])]))
|
||||||
|
|
||||||
(defview member-photo [from & [identicon size]]
|
;; We optionally pass identicon for perfomance reason, so it does not have to be calculated for each message
|
||||||
(letsubs [photo-path [:chats/photo-path from]]
|
(defn member-photo [pub-key identicon]
|
||||||
(photo (or photo-path identicon)
|
(let [path @(re-frame/subscribe [:chats/photo-path pub-key identicon])]
|
||||||
{:accessibility-label :member-photo
|
[photo path {:size style/default-size
|
||||||
:size (or size style/default-size)})))
|
:accessibility-label :member-photo}]))
|
||||||
|
|
||||||
|
(defn account-photo [account]
|
||||||
|
(let [path (multiaccounts/displayed-photo account)]
|
||||||
|
[photo path {:size style/default-size
|
||||||
|
:accessibility-label :own-account-photo}]))
|
||||||
|
|
||||||
(defn member-identicon [identicon]
|
(defn member-identicon [identicon]
|
||||||
(let [size style/default-size]
|
(let [size style/default-size]
|
||||||
|
@ -376,7 +376,7 @@
|
|||||||
wizard-state)]]]))
|
wizard-state)]]]))
|
||||||
|
|
||||||
(defview wizard-recovery-success []
|
(defview wizard-recovery-success []
|
||||||
(letsubs [{:keys [pubkey processing? name photo-path]} [:intro-wizard/recovery-success]
|
(letsubs [{:keys [pubkey processing? name identicon]} [:intro-wizard/recovery-success]
|
||||||
existing-account? [:intro-wizard/recover-existing-account?]]
|
existing-account? [:intro-wizard/recover-existing-account?]]
|
||||||
[react/view {:style {:flex 1}}
|
[react/view {:style {:flex 1}}
|
||||||
[topbar/topbar
|
[topbar/topbar
|
||||||
@ -386,7 +386,7 @@
|
|||||||
[react/view {:style {:flex 1
|
[react/view {:style {:flex 1
|
||||||
:justify-content :space-between}}
|
:justify-content :space-between}}
|
||||||
[top-bar {:step :recovery-success}]
|
[top-bar {:step :recovery-success}]
|
||||||
[recovery-success pubkey name photo-path]
|
[recovery-success pubkey name identicon]
|
||||||
[bottom-bar {:step :recovery-success
|
[bottom-bar {:step :recovery-success
|
||||||
:forward-action :multiaccounts.recover/re-encrypt-pressed
|
:forward-action :multiaccounts.recover/re-encrypt-pressed
|
||||||
:processing? processing?
|
:processing? processing?
|
||||||
|
@ -166,8 +166,8 @@
|
|||||||
{:should-component-update
|
{:should-component-update
|
||||||
(fn [_ [_ old-account] [_ new-account]]
|
(fn [_ [_ old-account] [_ new-account]]
|
||||||
(and (not (nil? new-account))
|
(and (not (nil? new-account))
|
||||||
(and (not (:photo-path old-account))
|
(and (not (:identicon old-account))
|
||||||
(nil? (:photo-path new-account)))))
|
(nil? (:identicon new-account)))))
|
||||||
|
|
||||||
:reagent-render
|
:reagent-render
|
||||||
(fn [account small-screen?]
|
(fn [account small-screen?]
|
||||||
|
@ -24,14 +24,12 @@
|
|||||||
(defn multiaccount-login-badge [{:keys [public-key name] :as multiaccount}]
|
(defn multiaccount-login-badge [{:keys [public-key name] :as multiaccount}]
|
||||||
[react/view styles/login-badge
|
[react/view styles/login-badge
|
||||||
[photos/photo
|
[photos/photo
|
||||||
;;TODO this should be done in a subscription
|
|
||||||
(multiaccounts/displayed-photo multiaccount)
|
(multiaccounts/displayed-photo multiaccount)
|
||||||
{:size styles/login-badge-image-size}]
|
{:size styles/login-badge-image-size}]
|
||||||
[react/view
|
[react/view
|
||||||
[react/text {:style styles/login-badge-name
|
[react/text {:style styles/login-badge-name
|
||||||
:ellipsize-mode :middle
|
:ellipsize-mode :middle
|
||||||
:numberOfLines 1}
|
:numberOfLines 1}
|
||||||
;;TODO this should be done in a subscription
|
|
||||||
name]
|
name]
|
||||||
[quo/text {:monospace true
|
[quo/text {:monospace true
|
||||||
:align :center
|
:align :center
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
(:require-macros [status-im.utils.views :refer [defview letsubs]])
|
(:require-macros [status-im.utils.views :refer [defview letsubs]])
|
||||||
(:require [re-frame.core :as re-frame]
|
(:require [re-frame.core :as re-frame]
|
||||||
[status-im.ui.screens.chat.photos :as photos]
|
[status-im.ui.screens.chat.photos :as photos]
|
||||||
|
[status-im.multiaccounts.core :as multiaccounts]
|
||||||
[status-im.ui.screens.multiaccounts.styles :as styles]
|
[status-im.ui.screens.multiaccounts.styles :as styles]
|
||||||
[status-im.ui.components.list.views :as list]
|
[status-im.ui.components.list.views :as list]
|
||||||
[status-im.ui.components.react :as react]
|
[status-im.ui.components.react :as react]
|
||||||
@ -14,10 +15,10 @@
|
|||||||
[status-im.react-native.resources :as resources]))
|
[status-im.react-native.resources :as resources]))
|
||||||
|
|
||||||
(defn multiaccount-view
|
(defn multiaccount-view
|
||||||
[{:keys [key-uid photo-path name keycard-pairing]}]
|
[{:keys [key-uid name keycard-pairing] :as account}]
|
||||||
[quo/list-item {:on-press #(re-frame/dispatch
|
[quo/list-item {:on-press #(re-frame/dispatch
|
||||||
[:multiaccounts.login.ui/multiaccount-selected key-uid])
|
[:multiaccounts.login.ui/multiaccount-selected key-uid])
|
||||||
:icon [photos/photo photo-path {:size styles/multiaccount-image-size}]
|
:icon [photos/photo (multiaccounts/displayed-photo account) {:size styles/multiaccount-image-size}]
|
||||||
:title name
|
:title name
|
||||||
:accessory (when keycard-pairing
|
:accessory (when keycard-pairing
|
||||||
[react/view {:justify-content :center
|
[react/view {:justify-content :center
|
||||||
|
@ -1,48 +1,9 @@
|
|||||||
(ns status-im.ui.screens.profile.events
|
(ns status-im.ui.screens.profile.events
|
||||||
(:require [re-frame.core :as re-frame]
|
(:require [re-frame.core :as re-frame]
|
||||||
[status-im.multiaccounts.model :as multiaccounts.model]
|
|
||||||
[status-im.ui.screens.profile.models :as profile.models]
|
[status-im.ui.screens.profile.models :as profile.models]
|
||||||
[status-im.ui.components.list-selection :as list-selection]
|
[status-im.ui.components.list-selection :as list-selection]
|
||||||
[status-im.utils.handlers :as handlers]
|
[status-im.utils.handlers :as handlers]
|
||||||
[status-im.utils.identicon :as identicon]
|
[status-im.utils.universal-links.utils :as universal-links]))
|
||||||
[status-im.utils.universal-links.utils :as universal-links]
|
|
||||||
[status-im.utils.fx :as fx]))
|
|
||||||
|
|
||||||
(handlers/register-handler-fx
|
|
||||||
:profile/send-transaction
|
|
||||||
(fn [cofx [_ chat-id]]
|
|
||||||
(profile.models/send-transaction chat-id cofx)))
|
|
||||||
|
|
||||||
(handlers/register-handler-fx
|
|
||||||
:my-profile/update-name
|
|
||||||
(fn [cofx [_ name]]
|
|
||||||
(profile.models/update-name name cofx)))
|
|
||||||
|
|
||||||
(handlers/register-handler-fx
|
|
||||||
:my-profile/remove-current-photo
|
|
||||||
(fn [{:keys [db] :as cofx}]
|
|
||||||
(fx/merge cofx
|
|
||||||
{:db (-> db
|
|
||||||
(assoc-in [:my-profile/profile :photo-path]
|
|
||||||
(identicon/identicon (multiaccounts.model/current-public-key cofx)))
|
|
||||||
(assoc :my-profile/editing? true
|
|
||||||
:profile/photo-added? false))}
|
|
||||||
(profile.models/save))))
|
|
||||||
|
|
||||||
(handlers/register-handler-fx
|
|
||||||
:my-profile/start-editing-profile
|
|
||||||
(fn [cofx _]
|
|
||||||
(profile.models/start-editing cofx)))
|
|
||||||
|
|
||||||
(handlers/register-handler-fx
|
|
||||||
:my-profile/save-profile
|
|
||||||
(fn [cofx _]
|
|
||||||
(profile.models/save cofx)))
|
|
||||||
|
|
||||||
(handlers/register-handler-fx
|
|
||||||
:group-chat-profile/start-editing
|
|
||||||
(fn [cofx _]
|
|
||||||
(profile.models/start-editing-group-chat-profile cofx)))
|
|
||||||
|
|
||||||
(handlers/register-handler-fx
|
(handlers/register-handler-fx
|
||||||
:my-profile/enter-two-random-words
|
:my-profile/enter-two-random-words
|
||||||
|
@ -1,57 +1,11 @@
|
|||||||
(ns status-im.ui.screens.profile.models
|
(ns status-im.ui.screens.profile.models
|
||||||
(:require [clojure.spec.alpha :as spec]
|
(:require [clojure.string :as clojure.string]
|
||||||
[clojure.string :as clojure.string]
|
|
||||||
[re-frame.core :as re-frame]
|
[re-frame.core :as re-frame]
|
||||||
[status-im.ui.components.react :as react]
|
[status-im.ui.components.react :as react]
|
||||||
[status-im.multiaccounts.update.core :as multiaccounts.update]
|
[status-im.multiaccounts.update.core :as multiaccounts.update]
|
||||||
[status-im.chat.models :as chat-models]
|
|
||||||
[taoensso.timbre :as log]
|
[taoensso.timbre :as log]
|
||||||
[status-im.utils.fx :as fx]))
|
[status-im.utils.fx :as fx]))
|
||||||
|
|
||||||
(defn send-transaction [chat-id cofx]
|
|
||||||
;;TODO start send transaction command flow
|
|
||||||
(chat-models/start-chat cofx chat-id))
|
|
||||||
|
|
||||||
(defn- valid-name? [name]
|
|
||||||
(spec/valid? :profile/name name))
|
|
||||||
|
|
||||||
(defn update-name [name {:keys [db]}]
|
|
||||||
{:db (-> db
|
|
||||||
(assoc-in [:my-profile/profile :valid-name?] (valid-name? name))
|
|
||||||
(assoc-in [:my-profile/profile :name] name))})
|
|
||||||
|
|
||||||
(defn- clean-name [db edit-view]
|
|
||||||
(let [name (get-in db [edit-view :name])]
|
|
||||||
(if (valid-name? name)
|
|
||||||
name
|
|
||||||
(get-in db [:multiaccount :name]))))
|
|
||||||
|
|
||||||
(fx/defn clear-profile
|
|
||||||
[{:keys [db]}]
|
|
||||||
{:db (dissoc db :my-profile/profile :my-profile/default-name :my-profile/editing?)})
|
|
||||||
|
|
||||||
(defn start-editing [{:keys [db]}]
|
|
||||||
(let [profile (select-keys (:multiaccount db) [:name :photo-path])]
|
|
||||||
{:db (assoc db
|
|
||||||
:my-profile/editing? true
|
|
||||||
:my-profile/profile profile)}))
|
|
||||||
|
|
||||||
(fx/defn save [{:keys [db now] :as cofx}]
|
|
||||||
(let [{:keys [photo-path]} (:my-profile/profile db)
|
|
||||||
cleaned-name (clean-name db :my-profile/profile)]
|
|
||||||
(fx/merge cofx
|
|
||||||
(clear-profile)
|
|
||||||
(multiaccounts.update/multiaccount-update :name cleaned-name {})
|
|
||||||
(multiaccounts.update/multiaccount-update :last-updated now {})
|
|
||||||
(when photo-path
|
|
||||||
(multiaccounts.update/multiaccount-update :photo-path photo-path {})))))
|
|
||||||
|
|
||||||
(defn start-editing-group-chat-profile [{:keys [db]}]
|
|
||||||
(let [current-chat-name (get-in db [:chats (:current-chat-id db) :name])]
|
|
||||||
{:db (-> db
|
|
||||||
(assoc :group-chat-profile/editing? true)
|
|
||||||
(assoc-in [:group-chat-profile/profile :name] current-chat-name))}))
|
|
||||||
|
|
||||||
(defn enter-two-random-words [{:keys [db]}]
|
(defn enter-two-random-words [{:keys [db]}]
|
||||||
(let [{:keys [mnemonic]} (:multiaccount db)
|
(let [{:keys [mnemonic]} (:multiaccount db)
|
||||||
shuffled-mnemonic (shuffle (map-indexed vector (clojure.string/split mnemonic #" ")))]
|
shuffled-mnemonic (shuffle (map-indexed vector (clojure.string/split mnemonic #" ")))]
|
||||||
@ -62,7 +16,7 @@
|
|||||||
(defn set-step [step {:keys [db]}]
|
(defn set-step [step {:keys [db]}]
|
||||||
{:db (update db :my-profile/seed assoc :step step :error nil :word nil)})
|
{:db (update db :my-profile/seed assoc :step step :error nil :word nil)})
|
||||||
|
|
||||||
(defn finish [{:keys [db] :as cofx}]
|
(fx/defn finish [{:keys [db] :as cofx}]
|
||||||
(fx/merge cofx
|
(fx/merge cofx
|
||||||
{:db (update db :my-profile/seed assoc :step :finish :error nil :word nil)}
|
{:db (update db :my-profile/seed assoc :step :finish :error nil :word nil)}
|
||||||
(multiaccounts.update/clean-seed-phrase)))
|
(multiaccounts.update/clean-seed-phrase)))
|
||||||
|
44
src/status_im/ui/screens/profile/user/edit_picture.cljs
Normal file
44
src/status_im/ui/screens/profile/user/edit_picture.cljs
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
(ns status-im.ui.screens.profile.user.edit-picture
|
||||||
|
(:require [quo.core :as quo]
|
||||||
|
[re-frame.core :as re-frame]
|
||||||
|
[status-im.i18n :as i18n]
|
||||||
|
[status-im.utils.config :as config]
|
||||||
|
[status-im.multiaccounts.core :as multiaccounts]
|
||||||
|
[status-im.ui.components.react :as react]))
|
||||||
|
|
||||||
|
(def crop-size 1000)
|
||||||
|
(def crop-opts {:cropping true
|
||||||
|
:cropperCircleOverlay true
|
||||||
|
:width crop-size
|
||||||
|
:height crop-size})
|
||||||
|
|
||||||
|
(defn pick-pic []
|
||||||
|
(react/show-image-picker
|
||||||
|
#(re-frame/dispatch [::multiaccounts/save-profile-picture (.-path ^js %) 0 0 crop-size crop-size])
|
||||||
|
crop-opts))
|
||||||
|
|
||||||
|
(defn take-pic []
|
||||||
|
(react/show-image-picker-camera
|
||||||
|
#(re-frame/dispatch [::multiaccounts/save-profile-picture (.-path ^js %) 0 0 crop-size crop-size])
|
||||||
|
crop-opts))
|
||||||
|
|
||||||
|
(defn bottom-sheet [has-picture]
|
||||||
|
(fn []
|
||||||
|
[:<>
|
||||||
|
[quo/list-item {:accessibility-label :take-photo
|
||||||
|
:theme :accent
|
||||||
|
:icon :main-icons/camera
|
||||||
|
:title (i18n/label :t/profile-pic-take)
|
||||||
|
:on-press take-pic}]
|
||||||
|
[quo/list-item {:accessibility-label :pick-photo
|
||||||
|
:icon :main-icons/gallery
|
||||||
|
:theme :accent
|
||||||
|
:title (i18n/label :t/profile-pic-pick)
|
||||||
|
:on-press pick-pic}]
|
||||||
|
(when (and config/enable-remove-profile-picture?
|
||||||
|
has-picture)
|
||||||
|
[quo/list-item {:accessibility-label :remove-photo
|
||||||
|
:icon :main-icons/delete
|
||||||
|
:theme :accent
|
||||||
|
:title (i18n/label :t/profile-pic-remove)
|
||||||
|
:on-press #(re-frame/dispatch [::multiaccounts/delete-profile-picture nil])}])]))
|
@ -16,6 +16,7 @@
|
|||||||
[status-im.utils.gfycat.core :as gfy]
|
[status-im.utils.gfycat.core :as gfy]
|
||||||
[status-im.utils.universal-links.utils :as universal-links]
|
[status-im.utils.universal-links.utils :as universal-links]
|
||||||
[status-im.ui.components.profile-header.view :as profile-header]
|
[status-im.ui.components.profile-header.view :as profile-header]
|
||||||
|
[status-im.ui.screens.profile.user.edit-picture :as edit]
|
||||||
[status-im.utils.utils :as utils]
|
[status-im.utils.utils :as utils]
|
||||||
[status-im.ethereum.stateofus :as stateofus])
|
[status-im.ethereum.stateofus :as stateofus])
|
||||||
(:require-macros [status-im.utils.views :as views]))
|
(:require-macros [status-im.utils.views :as views]))
|
||||||
@ -167,10 +168,11 @@
|
|||||||
(fn []
|
(fn []
|
||||||
(let [{:keys [public-key ens-verified preferred-name]
|
(let [{:keys [public-key ens-verified preferred-name]
|
||||||
:as account} @(re-frame/subscribe [:multiaccount])
|
:as account} @(re-frame/subscribe [:multiaccount])
|
||||||
on-share #(re-frame/dispatch [:show-popover
|
on-share #(re-frame/dispatch [:show-popover
|
||||||
{:view :share-chat-key
|
{:view :share-chat-key
|
||||||
:address public-key
|
:address public-key
|
||||||
:ens-name preferred-name}])]
|
:ens-name preferred-name}])
|
||||||
|
has-picture @(re-frame/subscribe [:profile/has-picture])]
|
||||||
[react/view {:flex 1}
|
[react/view {:flex 1}
|
||||||
[quo/animated-header
|
[quo/animated-header
|
||||||
{:right-accessories [{:accessibility-label :share-header-button
|
{:right-accessories [{:accessibility-label :share-header-button
|
||||||
@ -178,11 +180,13 @@
|
|||||||
:on-press on-share}]
|
:on-press on-share}]
|
||||||
:use-insets true
|
:use-insets true
|
||||||
:extended-header (profile-header/extended-header
|
:extended-header (profile-header/extended-header
|
||||||
{:on-press on-share
|
{:on-press on-share
|
||||||
:title (multiaccounts/displayed-name account)
|
:on-edit #(re-frame/dispatch [:bottom-sheet/show-sheet
|
||||||
:photo (multiaccounts/displayed-photo account)
|
{:content (edit/bottom-sheet has-picture)}])
|
||||||
:monospace (not ens-verified)
|
:title (multiaccounts/displayed-name account)
|
||||||
:subtitle (if (and ens-verified public-key)
|
:photo (multiaccounts/displayed-photo account)
|
||||||
(gfy/generate-gfy public-key)
|
:monospace (not ens-verified)
|
||||||
(utils/get-shortened-address public-key))})}
|
:subtitle (if (and ens-verified public-key)
|
||||||
|
(gfy/generate-gfy public-key)
|
||||||
|
(utils/get-shortened-address public-key))})}
|
||||||
[content]]])))
|
[content]]])))
|
||||||
|
@ -17,7 +17,6 @@
|
|||||||
[status-im.ui.screens.chat.photos :as photos]
|
[status-im.ui.screens.chat.photos :as photos]
|
||||||
[status-im.ui.components.tabs :as tabs]
|
[status-im.ui.components.tabs :as tabs]
|
||||||
[status-im.utils.contenthash :as contenthash]
|
[status-im.utils.contenthash :as contenthash]
|
||||||
[status-im.multiaccounts.core :as multiaccounts]
|
|
||||||
[status-im.ui.screens.chat.message.reactions :as reactions]
|
[status-im.ui.screens.chat.message.reactions :as reactions]
|
||||||
[status-im.chat.models.reactions :as models.reactions]
|
[status-im.chat.models.reactions :as models.reactions]
|
||||||
[status-im.ui.screens.chat.components.reply :as components.reply]
|
[status-im.ui.screens.chat.components.reply :as components.reply]
|
||||||
@ -101,7 +100,7 @@
|
|||||||
[message-content-image (:image content) false]]])))
|
[message-content-image (:image content) false]]])))
|
||||||
|
|
||||||
(defn message-item [account]
|
(defn message-item [account]
|
||||||
(fn [{:keys [content-type content from timestamp identicon outgoing] :as message}
|
(fn [{:keys [content-type content from timestamp outgoing] :as message}
|
||||||
{:keys [modal on-long-press close-modal]}]
|
{:keys [modal on-long-press close-modal]}]
|
||||||
[react/view (merge {:padding-vertical 8
|
[react/view (merge {:padding-vertical 8
|
||||||
:flex-direction :row
|
:flex-direction :row
|
||||||
@ -114,8 +113,8 @@
|
|||||||
(re-frame/dispatch [:chat.ui/show-profile-without-adding-contact from]))}
|
(re-frame/dispatch [:chat.ui/show-profile-without-adding-contact from]))}
|
||||||
[react/view {:padding-top 2 :padding-right 8}
|
[react/view {:padding-top 2 :padding-right 8}
|
||||||
(if outgoing
|
(if outgoing
|
||||||
[photos/member-identicon (multiaccounts/displayed-photo account)]
|
[photos/account-photo account]
|
||||||
[photos/member-identicon identicon])]]
|
[photos/member-photo from])]]
|
||||||
[react/view {:flex 1}
|
[react/view {:flex 1}
|
||||||
[react/view {:flex-direction :row
|
[react/view {:flex-direction :row
|
||||||
:justify-content :space-between}
|
:justify-content :space-between}
|
||||||
|
@ -55,6 +55,8 @@
|
|||||||
(def pow-target (js/parseFloat (get-config :POW_TARGET "0.0001")))
|
(def pow-target (js/parseFloat (get-config :POW_TARGET "0.0001")))
|
||||||
(def pow-time (js/parseInt (get-config :POW_TIME "1")))
|
(def pow-time (js/parseInt (get-config :POW_TIME "1")))
|
||||||
(def max-installations 2)
|
(def max-installations 2)
|
||||||
|
; currently not supported in status-go
|
||||||
|
(def enable-remove-profile-picture? false)
|
||||||
|
|
||||||
(def verify-transaction-chain-id (js/parseInt (get-config :VERIFY_TRANSACTION_CHAIN_ID "1")))
|
(def verify-transaction-chain-id (js/parseInt (get-config :VERIFY_TRANSACTION_CHAIN_ID "1")))
|
||||||
(def verify-transaction-url (if (= :mainnet (ethereum/chain-id->chain-keyword verify-transaction-chain-id))
|
(def verify-transaction-url (if (= :mainnet (ethereum/chain-id->chain-keyword verify-transaction-chain-id))
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
"_comment": "DO NOT EDIT THIS FILE BY HAND. USE 'scripts/update-status-go.sh <tag>' instead",
|
"_comment": "DO NOT EDIT THIS FILE BY HAND. USE 'scripts/update-status-go.sh <tag>' instead",
|
||||||
"owner": "status-im",
|
"owner": "status-im",
|
||||||
"repo": "status-go",
|
"repo": "status-go",
|
||||||
"version": "v0.64.8",
|
"version": "v0.65.0",
|
||||||
"commit-sha1": "50b17308bde0008daf4c8365782575d4f22b1515",
|
"commit-sha1": "cdca42b90f7fd5f302a5eb31802b9ae526d566d7",
|
||||||
"src-sha256": "140xbx3xlzgcbp3iv98if9gbjslmg94gpzzbwqa303fh6mg460fw"
|
"src-sha256": "1qpq9y099bfa6x36afbimn2p5inzrsgbb8qzigmchl513mkhp5s1"
|
||||||
}
|
}
|
||||||
|
@ -529,6 +529,9 @@
|
|||||||
"image-source-gallery": "Select from gallery",
|
"image-source-gallery": "Select from gallery",
|
||||||
"image-source-make-photo": "Capture",
|
"image-source-make-photo": "Capture",
|
||||||
"image-source-title": "Edit picture",
|
"image-source-title": "Edit picture",
|
||||||
|
"profile-pic-take": "Take photo",
|
||||||
|
"profile-pic-pick": "Select from gallery",
|
||||||
|
"profile-pic-remove": "Remove photo",
|
||||||
"in-contacts": "In contacts",
|
"in-contacts": "In contacts",
|
||||||
"incoming": "Incoming",
|
"incoming": "Incoming",
|
||||||
"incoming-transaction": "Incoming transaction",
|
"incoming-transaction": "Incoming transaction",
|
||||||
|
Loading…
x
Reference in New Issue
Block a user