refactor: never save mnemonic in memory unless totally necessary

Necessary cases are:
- Onboarding to show the list of 5 accounts
- In QML when we show it to the user for the backup
  - Change it to a Loader, so the component and its memory is cleaned when closed
This commit is contained in:
Jonathan Rainville 2020-08-25 16:19:46 -04:00 committed by Iuri Matias
parent c79ccaded4
commit bd9e1619fa
5 changed files with 103 additions and 99 deletions

View File

@ -33,7 +33,6 @@ proc init*(self: ProfileController, account: Account) =
let profile = account.toProfileModel() let profile = account.toProfileModel()
let pubKey = status_settings.getSetting[string](Setting.PublicKey, "0x0") let pubKey = status_settings.getSetting[string](Setting.PublicKey, "0x0")
let mnemonic = status_settings.getSetting[string](Setting.Mnemonic, "")
let network = status_settings.getSetting[string](Setting.Networks_CurrentNetwork, constants.DEFAULT_NETWORK_NAME) let network = status_settings.getSetting[string](Setting.Networks_CurrentNetwork, constants.DEFAULT_NETWORK_NAME)
let appearance = status_settings.getSetting[int](Setting.Appearance) let appearance = status_settings.getSetting[int](Setting.Appearance)
profile.appearance = appearance profile.appearance = appearance
@ -43,7 +42,6 @@ proc init*(self: ProfileController, account: Account) =
self.view.addDevices(devices.getAllDevices()) self.view.addDevices(devices.getAllDevices())
self.view.setDeviceSetup(devices.isDeviceSetup()) self.view.setDeviceSetup(devices.isDeviceSetup())
self.view.setNewProfile(profile) self.view.setNewProfile(profile)
self.view.setMnemonic(mnemonic)
self.view.setNetwork(network) self.view.setNetwork(network)
self.view.ens.init() self.view.ens.init()

View File

@ -4,6 +4,7 @@ import ../../status/profile/[mailserver, profile, devices]
import ../../status/profile as status_profile import ../../status/profile as status_profile
import ../../status/contacts as status_contacts import ../../status/contacts as status_contacts
import ../../status/accounts as status_accounts import ../../status/accounts as status_accounts
import ../../status/libstatus/settings as status_settings
import ../../status/status import ../../status/status
import ../../status/devices as status_devices import ../../status/devices as status_devices
import ../../status/ens as status_ens import ../../status/ens as status_ens
@ -19,7 +20,6 @@ QtObject:
addedContacts*: ContactList addedContacts*: ContactList
blockedContacts*: ContactList blockedContacts*: ContactList
deviceList*: DeviceList deviceList*: DeviceList
mnemonic: string
network: string network: string
status*: Status status*: Status
isDeviceSetup: bool isDeviceSetup: bool
@ -50,7 +50,6 @@ QtObject:
result.blockedContacts = newContactList() result.blockedContacts = newContactList()
result.deviceList = newDeviceList() result.deviceList = newDeviceList()
result.ens = newEnsManager(status) result.ens = newEnsManager(status)
result.mnemonic = ""
result.network = "" result.network = ""
result.status = status result.status = status
result.isDeviceSetup = false result.isDeviceSetup = false
@ -109,19 +108,13 @@ QtObject:
read = getBlockedContacts read = getBlockedContacts
notify = contactListChanged notify = contactListChanged
proc mnemonicChanged*(self: ProfileView) {.signal.}
proc getMnemonic*(self: ProfileView): QVariant {.slot.} = proc getMnemonic*(self: ProfileView): QVariant {.slot.} =
return newQVariant(self.mnemonic) # Do not keep the mnemonic in memory, so fetch it when necessary
let mnemonic = status_settings.getSetting[string](Setting.Mnemonic, "")
proc setMnemonic*(self: ProfileView, mnemonic: string) = return newQVariant(mnemonic)
self.mnemonic = mnemonic
self.mnemonicChanged()
QtProperty[QVariant] mnemonic: QtProperty[QVariant] mnemonic:
read = getMnemonic read = getMnemonic
write = setMnemonic
notify = mnemonicChanged
proc networkChanged*(self: ProfileView) {.signal.} proc networkChanged*(self: ProfileView) {.signal.}

View File

@ -72,17 +72,21 @@ proc mainProc() =
var profile = profile.newController(status, changeLanguage) var profile = profile.newController(status, changeLanguage)
engine.setRootContextProperty("profileModel", profile.variant) engine.setRootContextProperty("profileModel", profile.variant)
var login = login.newController(status)
var onboarding = onboarding.newController(status)
status.events.once("login") do(a: Args): status.events.once("login") do(a: Args):
var args = AccountArgs(a) var args = AccountArgs(a)
# Delete login and onboarding from memory to remove any mnemonic that would have been saved in the accounts list
login.delete()
onboarding.delete()
status.startMessenger() status.startMessenger()
profile.init(args.account) profile.init(args.account)
wallet.init() wallet.init()
chat.init() chat.init()
var login = login.newController(status)
var onboarding = onboarding.newController(status)
engine.setRootContextProperty("loginModel", login.variant) engine.setRootContextProperty("loginModel", login.variant)
engine.setRootContextProperty("onboardingModel", onboarding.variant) engine.setRootContextProperty("onboardingModel", onboarding.variant)

View File

@ -10,17 +10,21 @@ ModalPopup {
//% "Write down your seed phrase" //% "Write down your seed phrase"
title: qsTrId("write-down-your-seed-phrase") title: qsTrId("write-down-your-seed-phrase")
Item { Loader {
active: popup.opened
width: parent.width
height: item.height
sourceComponent: Component {
id: seedComponent
Item {
id: seed id: seed
anchors.left: parent.left
anchors.right: parent.right
width: parent.width width: parent.width
height: children[0].height height: children[0].height
Rectangle { Rectangle {
id: wrapper id: wrapper
property int len: profileModel.mnemonic.split(" ").length property int len: mnemonicRepeater.count
anchors.top: parent.top anchors.top: parent.top
anchors.topMargin: Style.current.padding anchors.topMargin: Style.current.padding
height: 40 * (len / 2) height: 40 * (len / 2)
@ -32,13 +36,15 @@ ModalPopup {
anchors.horizontalCenter: parent.horizontalCenter anchors.horizontalCenter: parent.horizontalCenter
Repeater { Repeater {
id: mnemonicRepeater
model: profileModel.mnemonic.split(" ") model: profileModel.mnemonic.split(" ")
Rectangle { Rectangle {
id: word id: word
height: 40 height: 40
width: 175 width: 175
color: "transparent" color: "transparent"
anchors.top: (index == 0 || index == (wrapper.len/2)) ? parent.top : parent.children[index-1].bottom anchors.top: (index == 0
|| index == (wrapper.len / 2)) ? parent.top : parent.children[index - 1].bottom
anchors.left: (index < (wrapper.len / 2)) ? parent.left : undefined anchors.left: (index < (wrapper.len / 2)) ? parent.left : undefined
anchors.right: (index >= wrapper.len / 2) ? parent.right : undefined anchors.right: (index >= wrapper.len / 2) ? parent.right : undefined
@ -74,7 +80,8 @@ ModalPopup {
selectByMouse: true selectByMouse: true
readOnly: true readOnly: true
} }
}
}
} }
} }
} }
@ -83,7 +90,8 @@ ModalPopup {
StyledText { StyledText {
id: confirmationsInfo id: confirmationsInfo
//% "With this 12 words you can always get your key back. Write it down. Keep it safe, offline, and separate from this device." //% "With this 12 words you can always get your key back. Write it down. Keep it safe, offline, and separate from this device."
text: qsTrId("with-this-12-words-you-can-always-get-your-key-back.-write-it-down.-keep-it-safe,-offline,-and-separate-from-this-device.") text: qsTrId(
"with-this-12-words-you-can-always-get-your-key-back.-write-it-down.-keep-it-safe,-offline,-and-separate-from-this-device.")
font.pixelSize: 14 font.pixelSize: 14
font.weight: Font.Medium font.weight: Font.Medium
color: Style.current.darkGrey color: Style.current.darkGrey

View File

@ -152,6 +152,7 @@ DISTFILES += \
app/AppLayouts/Profile/LeftTab/components/MenuButton.qml \ app/AppLayouts/Profile/LeftTab/components/MenuButton.qml \
app/AppLayouts/Chat/data/EmojiReactions.qml \ app/AppLayouts/Chat/data/EmojiReactions.qml \
app/AppLayouts/Profile/Sections/AppearanceContainer.qml \ app/AppLayouts/Profile/Sections/AppearanceContainer.qml \
app/AppLayouts/Profile/Sections/BackupSeedModal.qml \
app/AppLayouts/Profile/Sections/MyProfileContainer.qml \ app/AppLayouts/Profile/Sections/MyProfileContainer.qml \
app/AppLayouts/Profile/Sections/SoundsContainer.qml \ app/AppLayouts/Profile/Sections/SoundsContainer.qml \
app/AppLayouts/Wallet/ReceiveModal.qml \ app/AppLayouts/Wallet/ReceiveModal.qml \