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,100 +10,108 @@ 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
id: seed sourceComponent: Component {
anchors.left: parent.left id: seedComponent
anchors.right: parent.right Item {
width: parent.width id: seed
height: children[0].height width: parent.width
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)
width: 350 width: 350
border.width: 1 border.width: 1
color: Style.current.background color: Style.current.background
border.color: Style.current.border border.color: Style.current.border
radius: Style.current.radius radius: Style.current.radius
anchors.horizontalCenter: parent.horizontalCenter anchors.horizontalCenter: parent.horizontalCenter
Repeater { Repeater {
model: profileModel.mnemonic.split(" ") id: mnemonicRepeater
Rectangle { model: profileModel.mnemonic.split(" ")
id: word Rectangle {
height: 40 id: word
width: 175 height: 40
color: "transparent" width: 175
anchors.top: (index == 0 || index == (wrapper.len/2)) ? parent.top : parent.children[index-1].bottom color: "transparent"
anchors.left: (index < (wrapper.len/2)) ? parent.left : undefined anchors.top: (index == 0
anchors.right: (index >= wrapper.len/2) ? parent.right : undefined || index == (wrapper.len / 2)) ? parent.top : parent.children[index - 1].bottom
anchors.left: (index < (wrapper.len / 2)) ? parent.left : undefined
anchors.right: (index >= wrapper.len / 2) ? parent.right : undefined
Rectangle { Rectangle {
width: 1 width: 1
height: parent.height height: parent.height
anchors.top: parent.top anchors.top: parent.top
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
anchors.right: parent.right anchors.right: parent.right
anchors.rightMargin: 175 anchors.rightMargin: 175
color: Style.current.inputBackground color: Style.current.inputBackground
visible: index >= wrapper.len/2 visible: index >= wrapper.len / 2
}
StyledText {
id: count
text: index + 1
color: Style.current.darkGrey
anchors.bottom: parent.bottom
anchors.bottomMargin: Style.current.smallPadding
anchors.left: parent.left
anchors.leftMargin: Style.current.bigPadding
font.pixelSize: 15
}
StyledTextEdit {
text: modelData
font.pixelSize: 15
anchors.bottom: parent.bottom
anchors.bottomMargin: Style.current.smallPadding
anchors.left: count.right
anchors.leftMargin: Style.current.padding
selectByMouse: true
readOnly: true
}
}
}
}
} }
StyledText {
id: count
text: index+1
color: Style.current.darkGrey
anchors.bottom: parent.bottom
anchors.bottomMargin: Style.current.smallPadding
anchors.left: parent.left
anchors.leftMargin: Style.current.bigPadding
font.pixelSize: 15
}
StyledTextEdit {
text: modelData
font.pixelSize: 15
anchors.bottom: parent.bottom
anchors.bottomMargin: Style.current.smallPadding
anchors.left: count.right
anchors.leftMargin: Style.current.padding
selectByMouse: true
readOnly: true
}
}
} }
}
} }
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(
font.pixelSize: 14 "with-this-12-words-you-can-always-get-your-key-back.-write-it-down.-keep-it-safe,-offline,-and-separate-from-this-device.")
font.weight: Font.Medium font.pixelSize: 14
color: Style.current.darkGrey font.weight: Font.Medium
anchors.bottom: parent.bottom color: Style.current.darkGrey
anchors.bottomMargin: Style.current.padding anchors.bottom: parent.bottom
anchors.left: parent.left anchors.bottomMargin: Style.current.padding
anchors.leftMargin: Style.current.smallPadding anchors.left: parent.left
anchors.right: parent.right anchors.leftMargin: Style.current.smallPadding
anchors.rightMargin: Style.current.smallPadding anchors.right: parent.right
wrapMode: Text.WordWrap anchors.rightMargin: Style.current.smallPadding
wrapMode: Text.WordWrap
} }
footer: StyledButton { footer: StyledButton {
//% "Done" //% "Done"
label: qsTrId("done") label: qsTrId("done")
anchors.right: parent.right anchors.right: parent.right
anchors.rightMargin: Style.current.smallPadding anchors.rightMargin: Style.current.smallPadding
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
onClicked: { onClicked: {
backupSeedModal.close() backupSeedModal.close()
} }
} }
} }

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 \