From 098b2af2abf00d224763bd8781681135d788c1cf Mon Sep 17 00:00:00 2001 From: varjolintu Date: Thu, 27 Apr 2023 16:22:13 +0300 Subject: [PATCH] Draft 270423 --- keepassxc-browser/background/event.js | 425 +++++++++--------- keepassxc-browser/background/httpauth.js | 2 +- keepassxc-browser/background/keepass.js | 15 +- keepassxc-browser/background/protocol.js | 44 +- .../background/protocolClient.js | 14 +- keepassxc-browser/popups/popup.js | 2 +- keepassxc-browser/popups/popup_login.js | 2 +- 7 files changed, 270 insertions(+), 234 deletions(-) diff --git a/keepassxc-browser/background/event.js b/keepassxc-browser/background/event.js index e9e33fb..3aed74f 100755 --- a/keepassxc-browser/background/event.js +++ b/keepassxc-browser/background/event.js @@ -2,6 +2,166 @@ const kpxcEvent = {}; +kpxcEvent.checkUpdateKeePassXC = async function() { + keepass.checkForNewKeePassXCVersion(); + return { current: keepass.currentKeePassXC.version, latest: keepass.latestKeePassXC.version }; +}; + +kpxcEvent.compareVersion = async function(tab, args = []) { + return keepass.compareVersion(args[0], args[1]); +}; + +kpxcEvent.getColorTheme = async function(tab) { + return page.settings.colorTheme; +}; + +kpxcEvent.getConnectedDatabase = async function() { + return Promise.resolve({ + count: Object.keys(keepass.keyRing).length, + identifier: (keepass.keyRing[keepass.associated.hash]) ? keepass.keyRing[keepass.associated.hash].id : null + }); +}; + +kpxcEvent.getIsKeePassXCAvailable = async function() { + return keepass.isKeePassXCAvailable; +}; + +kpxcEvent.getKeePassXCVersions = async function(tab) { + // TODO: Maybe this is not needed? + /*if (keepass.currentKeePassXC === '') { + await keepass.getDatabaseHash(tab); // TODO: How to get just the version? A separate API call? + return { 'current': keepass.currentKeePassXC, 'latest': keepass.latestKeePassXC.version }; + }*/ + + return { 'current': keepass.currentKeePassXC, 'latest': keepass.latestKeePassXC.version }; +}; + +// TODO: Refactor. This is ugly. internalPoll needs to be handled with V2. +kpxcEvent.getStatus = async function(tab, args = []) { + // When internalPoll is true the event is triggered from content script in intervals -> don't poll KeePassXC + try { + const [ internalPoll = false, triggerUnlock = false ] = args; + let configured = false; + + if (keepass.protocolV2) { + if (!internalPoll) { + const response = await protocol.testAssociationFromDatabaseStatuses(tab, [ true, triggerUnlock ]); + configured = response.isAnyAssociated; + } else { + // TODO: This does not update when db is locked or just opened + configured = keepass.databaseAssosiationStatuses?.isAnyAssociated; // ? + } + } else { + if (!internalPoll) { + const response = await keepassProtocol.testAssociation(tab, [ true, triggerUnlock ]); + if (!response) { + return kpxcEvent.showStatus(tab, false); + } + } + + configured = await keepass.isConfigured(); + } + + /*if (keepass.protocolV2) { + const response = await protocol.testAssociationFromDatabaseStatuses(tab, [ true, triggerUnlock ]); + configured = response.isAnyAssociated; + } else { + if (!internalPoll) { + const response = await keepassProtocol.testAssociation(tab, [ true, triggerUnlock ]); + if (!response) { + return kpxcEvent.showStatus(tab, false); + } + } + + configured = await keepass.isConfigured(); + }*/ + + return kpxcEvent.showStatus(tab, configured, internalPoll); + } catch (err) { + logError('No status shown: ' + err); + return Promise.reject(); + } +}; + +kpxcEvent.getTabInformation = async function(tab) { + const id = tab?.id || page.currentTabId; + return page.tabs[id]; +}; + +kpxcEvent.hideGettingStartedGuideAlert = async function(tab) { + const settings = await kpxcEvent.loadSettings(); + settings.showGettingStartedGuideAlert = false; + + await kpxcEvent.saveSettings(tab, settings); +}; + +kpxcEvent.hideTroubleshootingGuideAlert = async function(tab) { + const settings = await kpxcEvent.loadSettings(); + settings.showTroubleshootingGuideAlert = false; + + await kpxcEvent.saveSettings(tab, settings); +}; + +kpxcEvent.initHttpAuth = async function() { + httpAuth.init(); +}; + +kpxcEvent.initHttpAuthPopup = async function(tab, data) { + const popupData = { + iconType: 'questionmark', + popup: 'popup_httpauth' + }; + + page.tabs[tab.id].loginList = data; + browserAction.show(tab, popupData); +}; + +kpxcEvent.initLoginPopup = async function(tab, logins) { + const popupData = { + iconType: 'questionmark', + popup: 'popup_login' + }; + + page.tabs[tab.id].loginList = logins; + browserAction.show(tab, popupData); +}; + +kpxcEvent.loadKeyRing = async function() { + const item = await browser.storage.local.get({ 'keyRing': {} }).catch((err) => { + logError('kpxcEvent.loadKeyRing error: ' + err); + return Promise.reject(); + }); + + keepass.keyRing = item.keyRing; + // TODO: What to do here? + if (keepass.isAssociated() && !keepass.keyRing[keepass.associated.hash]) { + keepass.associated = { + value: false, + hash: null + }; + } + + return item.keyRing; +}; + +kpxcEvent.loadSettings = async function() { + return await page.initSettings().catch((err) => { + logError('loadSettings error: ' + err); + return Promise.reject(); + }); +}; + +kpxcEvent.lockDatabase = async function(tab) { + try { + await keepass.lockDatabase(tab); + return kpxcEvent.showStatus(tab, false); + } catch (err) { + logError('kpxcEvent.lockDatabase error: ' + err); + return false; + } +}; + +// Message handler kpxcEvent.onMessage = async function(request, sender) { if (request.action in kpxcEvent.messageHandlers) { if (!Object.hasOwn(sender, 'tab') || sender.tab.id < 1) { @@ -13,6 +173,54 @@ kpxcEvent.onMessage = async function(request, sender) { } }; +kpxcEvent.pageClearLogins = async function(tab, alreadyCalled) { + if (!alreadyCalled) { + page.clearLogins(tab.id); + } +}; + +kpxcEvent.pageGetRedirectCount = async function() { + return page.redirectCount; +}; + +kpxcEvent.passwordGetFilled = async function() { + return page.passwordFilled; +}; + +kpxcEvent.passwordSetFilled = async function(tab, state) { + page.passwordFilled = state; +}; + +kpxcEvent.reconnect = async function(tab) { + const configured = await keepass.reconnect(tab); + if (configured) { + browser.tabs.sendMessage(tab.id, { + action: 'redetect_fields' + }).catch((err) => { + logError(err); + return; + }); + } + + return kpxcEvent.showStatus(tab, configured); +}; + +kpxcEvent.removeCredentialsFromTabInformation = async function(tab) { + const id = tab?.id || page.currentTabId; + page.clearCredentials(id); + page.clearSubmittedCredentials(); +}; + +kpxcEvent.saveSettings = async function(tab, settings) { + browser.storage.local.set({ 'settings': settings }); + kpxcEvent.loadSettings(tab); +}; + +// Bounce message back to all frames +kpxcEvent.sendBackToTabs = async function(tab, args = []) { + await browser.tabs.sendMessage(tab.id, { action: 'frame_message', args: args }); +}; + kpxcEvent.showStatus = async function(tab, configured, internalPoll) { let keyId = null; if (configured && keepass.databaseHash !== '' && keepass.keyRing[keepass.databaseHash]) { @@ -41,206 +249,19 @@ kpxcEvent.showStatus = async function(tab, configured, internalPoll) { }; }; -kpxcEvent.onLoadSettings = async function() { - return await page.initSettings().catch((err) => { - logError('onLoadSettings error: ' + err); - return Promise.reject(); - }); -}; - -kpxcEvent.onLoadKeyRing = async function() { - const item = await browser.storage.local.get({ 'keyRing': {} }).catch((err) => { - logError('kpxcEvent.onLoadKeyRing error: ' + err); - return Promise.reject(); - }); - - keepass.keyRing = item.keyRing; - // TODO: What to do here? - if (keepass.isAssociated() && !keepass.keyRing[keepass.associated.hash]) { - keepass.associated = { - value: false, - hash: null - }; - } - - return item.keyRing; -}; - -kpxcEvent.onSaveSettings = async function(tab, settings) { - browser.storage.local.set({ 'settings': settings }); - kpxcEvent.onLoadSettings(tab); -}; - -kpxcEvent.onGetStatus = async function(tab, args = []) { - // When internalPoll is true the event is triggered from content script in intervals -> don't poll KeePassXC - try { - const [ internalPoll = false, triggerUnlock = false ] = args; - let configured = false; - - if (keepass.protocolV2) { - const response = await protocol.testAssociationFromDatabaseStatuses(tab, [ true, triggerUnlock ]); - configured = response.isAnyAssociated; - } else { - if (!internalPoll) { - const response = await keepassProtocol.testAssociation(tab, [ true, triggerUnlock ]); - if (!response) { - return kpxcEvent.showStatus(tab, false); - } - } - - configured = await keepass.isConfigured(); - } - - return kpxcEvent.showStatus(tab, configured, internalPoll); - } catch (err) { - logError('No status shown: ' + err); - return Promise.reject(); - } -}; - -kpxcEvent.onReconnect = async function(tab) { - const configured = await keepass.reconnect(tab); - if (configured) { - browser.tabs.sendMessage(tab.id, { - action: 'redetect_fields' - }).catch((err) => { - logError(err); - return; - }); - } - - return kpxcEvent.showStatus(tab, configured); -}; - -kpxcEvent.lockDatabase = async function(tab) { - try { - await keepass.lockDatabase(tab); - return kpxcEvent.showStatus(tab, false); - } catch (err) { - logError('kpxcEvent.lockDatabase error: ' + err); - return false; - } -}; - -kpxcEvent.onGetTabInformation = async function(tab) { - const id = tab?.id || page.currentTabId; - return page.tabs[id]; -}; - -kpxcEvent.onGetConnectedDatabase = async function() { - return Promise.resolve({ - count: Object.keys(keepass.keyRing).length, - identifier: (keepass.keyRing[keepass.associated.hash]) ? keepass.keyRing[keepass.associated.hash].id : null - }); -}; - -kpxcEvent.onGetKeePassXCVersions = async function(tab) { - // TODO: Maybe this is not needed? - /*if (keepass.currentKeePassXC === '') { - await keepass.getDatabaseHash(tab); // TODO: How to get just the version? A separate API call? - return { 'current': keepass.currentKeePassXC, 'latest': keepass.latestKeePassXC.version }; - }*/ - - return { 'current': keepass.currentKeePassXC, 'latest': keepass.latestKeePassXC.version }; -}; - -kpxcEvent.onCheckUpdateKeePassXC = async function() { - keepass.checkForNewKeePassXCVersion(); - return { current: keepass.currentKeePassXC.version, latest: keepass.latestKeePassXC.version }; -}; - -kpxcEvent.onUpdateAvailableKeePassXC = async function() { +kpxcEvent.updateAvailableKeePassXC = async function() { return (Number(page.settings.checkUpdateKeePassXC) !== CHECK_UPDATE_NEVER) ? keepass.keePassXCUpdateAvailable() : false; }; -kpxcEvent.onRemoveCredentialsFromTabInformation = async function(tab) { - const id = tab?.id || page.currentTabId; - page.clearCredentials(id); - page.clearSubmittedCredentials(); -}; - -kpxcEvent.onLoginPopup = async function(tab, logins) { - const popupData = { - iconType: 'questionmark', - popup: 'popup_login' - }; - - page.tabs[tab.id].loginList = logins; - browserAction.show(tab, popupData); -}; - -kpxcEvent.initHttpAuth = async function() { - httpAuth.init(); -}; - -kpxcEvent.onHTTPAuthPopup = async function(tab, data) { - const popupData = { - iconType: 'questionmark', - popup: 'popup_httpauth' - }; - - page.tabs[tab.id].loginList = data; - browserAction.show(tab, popupData); -}; - -kpxcEvent.onUsernameFieldDetected = async function(tab, detected) { +kpxcEvent.usernameFieldDetected = async function(tab, detected) { page.tabs[tab.id].usernameFieldDetected = detected; }; -kpxcEvent.passwordGetFilled = async function() { - return page.passwordFilled; -}; - -kpxcEvent.passwordSetFilled = async function(tab, state) { - page.passwordFilled = state; -}; - -kpxcEvent.getColorTheme = async function(tab) { - return page.settings.colorTheme; -}; - -kpxcEvent.pageGetRedirectCount = async function() { - return page.redirectCount; -}; - -kpxcEvent.pageClearLogins = async function(tab, alreadyCalled) { - if (!alreadyCalled) { - page.clearLogins(tab.id); - } -}; - -kpxcEvent.compareVersion = async function(tab, args = []) { - return keepass.compareVersion(args[0], args[1]); -}; - -kpxcEvent.getIsKeePassXCAvailable = async function() { - return keepass.isKeePassXCAvailable; -}; - -kpxcEvent.hideGettingStartedGuideAlert = async function(tab) { - const settings = await kpxcEvent.onLoadSettings(); - settings.showGettingStartedGuideAlert = false; - - await kpxcEvent.onSaveSettings(tab, settings); -}; - -kpxcEvent.hideTroubleshootingGuideAlert = async function(tab) { - const settings = await kpxcEvent.onLoadSettings(); - settings.showTroubleshootingGuideAlert = false; - - await kpxcEvent.onSaveSettings(tab, settings); -}; - -// Bounce message back to all frames -kpxcEvent.sendBackToTabs = async function(tab, args = []) { - await browser.tabs.sendMessage(tab.id, { action: 'frame_message', args: args }); -}; - // All methods named in this object have to be declared BEFORE this! kpxcEvent.messageHandlers = { 'associate': keepass.associate, 'check_database_hash': keepass.checkDatabaseHash, - 'check_update_keepassxc': kpxcEvent.onCheckUpdateKeePassXC, + 'check_update_keepassxc': kpxcEvent.checkUpdateKeePassXC, 'compare_version': kpxcEvent.compareVersion, 'create_credentials': keepass.createCredentials, 'create_new_group': keepass.createNewGroup, @@ -250,20 +271,20 @@ kpxcEvent.messageHandlers = { 'frame_message': kpxcEvent.sendBackToTabs, 'generate_password': keepass.generatePassword, 'get_color_theme': kpxcEvent.getColorTheme, - 'get_connected_database': kpxcEvent.onGetConnectedDatabase, + 'get_connected_database': kpxcEvent.getConnectedDatabase, 'get_database_hash': keepass.getDatabaseHash, // TODO ? 'get_database_groups': keepass.getDatabaseGroups, - 'get_keepassxc_versions': kpxcEvent.onGetKeePassXCVersions, + 'get_keepassxc_versions': kpxcEvent.getKeePassXCVersions, 'get_login_list': page.getLoginList, - 'get_status': kpxcEvent.onGetStatus, - 'get_tab_information': kpxcEvent.onGetTabInformation, + 'get_status': kpxcEvent.getStatus, + 'get_tab_information': kpxcEvent.getTabInformation, 'get_totp': keepass.getTotp, 'hide_getting_started_guide_alert': kpxcEvent.hideGettingStartedGuideAlert, 'hide_troubleshooting_guide_alert': kpxcEvent.hideTroubleshootingGuideAlert, 'init_http_auth': kpxcEvent.initHttpAuth, 'is_connected': kpxcEvent.getIsKeePassXCAvailable, - 'load_keyring': kpxcEvent.onLoadKeyRing, - 'load_settings': kpxcEvent.onLoadSettings, + 'load_keyring': kpxcEvent.loadKeyRing, + 'load_settings': kpxcEvent.loadSettings, 'lock_database': kpxcEvent.lockDatabase, 'page_clear_logins': kpxcEvent.pageClearLogins, 'page_clear_submitted': page.clearSubmittedCredentials, @@ -278,15 +299,15 @@ kpxcEvent.messageHandlers = { 'page_set_submitted': page.setSubmitted, 'password_get_filled': kpxcEvent.passwordGetFilled, 'password_set_filled': kpxcEvent.passwordSetFilled, - 'popup_login': kpxcEvent.onLoginPopup, - 'reconnect': kpxcEvent.onReconnect, - 'remove_credentials_from_tab_information': kpxcEvent.onRemoveCredentialsFromTabInformation, + 'popup_login': kpxcEvent.initLoginPopup, + 'reconnect': kpxcEvent.reconnect, + 'remove_credentials_from_tab_information': kpxcEvent.removeCredentialsFromTabInformation, 'request_autotype': keepass.requestAutotype, 'retrieve_credentials': page.retrieveCredentials, 'show_default_browseraction': browserAction.showDefault, 'update_credentials': keepass.updateCredentials, - 'username_field_detected': kpxcEvent.onUsernameFieldDetected, - 'save_settings': kpxcEvent.onSaveSettings, - 'update_available_keepassxc': kpxcEvent.onUpdateAvailableKeePassXC, + 'username_field_detected': kpxcEvent.usernameFieldDetected, + 'save_settings': kpxcEvent.saveSettings, + 'update_available_keepassxc': kpxcEvent.updateAvailableKeePassXC, 'update_context_menu': page.updateContextMenu }; diff --git a/keepassxc-browser/background/httpauth.js b/keepassxc-browser/background/httpauth.js index 4b5e61c..4d15bd7 100755 --- a/keepassxc-browser/background/httpauth.js +++ b/keepassxc-browser/background/httpauth.js @@ -90,7 +90,7 @@ httpAuth.loginOrShowCredentials = function(logins, details, resolve, reject) { if (page.settings.showNotifications) { showNotification(tr('multipleCredentialsDetected')); } - kpxcEvent.onHTTPAuthPopup({ 'id': details.tabId }, { 'logins': logins, 'url': details.searchUrl, 'resolve': resolve }); + kpxcEvent.initHttpAuthPopup({ 'id': details.tabId }, { 'logins': logins, 'url': details.searchUrl, 'resolve': resolve }); } } else { logError('No logins found for HTTP Basic Auth.'); diff --git a/keepassxc-browser/background/keepass.js b/keepassxc-browser/background/keepass.js index d608d87..330e204 100755 --- a/keepassxc-browser/background/keepass.js +++ b/keepassxc-browser/background/keepass.js @@ -2,6 +2,7 @@ const keepass = {}; keepass.associated = { 'value': false, 'hash': null }; +keepass.databaseAssosiationStatuses = {}; keepass.keyPair = { publicKey: null, secretKey: null }; keepass.serverPublicKey = ''; keepass.clientID = ''; @@ -88,7 +89,7 @@ browser.storage.local.get({ 'latestKeePassXC': { 'version': '', 'lastChecked': n }); //-------------------------------------------------------------------------- -// Command wrappers +// Command wrappers for events //-------------------------------------------------------------------------- keepass.associate = async function(tab, args = []) { @@ -123,6 +124,10 @@ keepass.lockDatabase = async function(tab, args = []) { return keepass.protocolV2 ? await protocol.lockDatabase(tab, args) : await keepassProtocol.lockDatabase(tab, args); }; +keepass.requestAutotype = async function(tab, args = []) { + return keepass.protocolV2 ? await protocol.requestAutotype(tab, args) : await keepassProtocol.requestAutotype(tab, args); +}; + keepass.updateCredentials = async function(tab, args = []) { return keepass.protocolV2 ? await protocol.updateCredentials(tab, args) : await keepassProtocol.updateCredentials(tab, args); }; @@ -205,6 +210,7 @@ keepass.deleteKey = function(hash) { browser.storage.local.set({ 'keyRing': keepass.keyRing }); }; +// Returns keys for the current active database keepass.getCryptoKey = function() { let dbkey = null; let dbid = null; @@ -263,7 +269,6 @@ keepass.reconnect = async function(tab, connectionTimeout) { return false; } - // What to do here? if (!keepass.protocolV2) { // Needed? const hash = await keepass.getDatabaseHash(tab); @@ -271,9 +276,11 @@ keepass.reconnect = async function(tab, connectionTimeout) { keepass.clearErrorMessage(tab); } - await keepass.testAssociation(); + await keepassProtocol.testAssociation(); await keepass.isConfigured(); } + + // TODO: What to do with Protocol V2? keepass.updateDatabaseHashToContent(); return true; }; @@ -312,7 +319,7 @@ keepass.isConfigured = async function() { return keepass.databaseHash in keepass.keyRing; }; -keepass.checkDatabaseHash = async function(tab) { +keepass.checkDatabaseHash = async function() { return keepass.databaseHash; }; diff --git a/keepassxc-browser/background/protocol.js b/keepassxc-browser/background/protocol.js index fe3440b..e512d65 100644 --- a/keepassxc-browser/background/protocol.js +++ b/keepassxc-browser/background/protocol.js @@ -14,16 +14,18 @@ protocol.associate = async function(tab, args = []) { try { keepass.clearErrorMessage(tab); - const key = protocolClient.getPublicConnectionKey(); + const publicKey = protocolClient.getPublicConnectionKey(); + const idKey = protocolClient.generateIdKey(); + const messageData = { action: kpActions.ASSOCIATE, - key: key, - idKey: protocolClient.generateIdKey() + publicKey: publicKey, + idKey: idKey }; const response = await protocolClient.sendMessage(tab, messageData, false, true); if (response && response.id && response.hash) { - keepass.setCryptoKey(response.id, key); // Save the new identification public key as id key for the database + keepass.setCryptoKey(response.id, idKey); browserAction.show(tab); return AssociatedAction.NEW_ASSOCIATION; @@ -99,6 +101,7 @@ protocol.createNewGroup = async function(tab, args = []) { const [ groupName ] = args; const [ dbid ] = keepass.getCryptoKey(); + const messageData = { action: kpActions.CREATE_NEW_GROUP, id: dbid, @@ -134,6 +137,7 @@ protocol.generatePassword = async function(tab, args = []) { // TODO: Return '' or [] ..? let password; + const messageData = { action: kpActions.GENERATE_PASSWORD, clientID: keepass.clientID, @@ -165,6 +169,7 @@ protocol.getCredentials = async function(tab, args = []) { const [ url, submiturl, triggerUnlock = false, httpAuth = false ] = args; let entries = []; + const messageData = { action: kpActions.GET_CREDENTIALS, url: url, @@ -183,6 +188,11 @@ protocol.getCredentials = async function(tab, args = []) { // TODO: Handle errors const response = await protocolClient.sendMessage(tab, messageData, false, triggerUnlock); if (response) { + if (response.error && response.errorCode) { + keepass.handleError(tab, response.errorCode); + return []; + } + entries = keepass.removeDuplicateEntries(response.entries); keepass.updateLastUsed(keepass.databaseHash); // What about this? @@ -198,7 +208,7 @@ protocol.getCredentials = async function(tab, args = []) { browserAction.showDefault(tab); return []; } catch (err) { - logError(`retrieveCredentials failed: ${err}`); + logError(`getCredentials failed: ${err}`); return []; } }; @@ -212,6 +222,7 @@ protocol.getDatabaseGroups = async function(tab, args = []) { const [ dbid ] = keepass.getCryptoKey(); let groups = []; + const messageData = { action: kpActions.GET_DATABASE_GROUPS, id: dbid @@ -247,6 +258,7 @@ protocol.getDatabaseStatuses = async function(tab, args = []) { } const [ enableTimeout = false, triggerUnlock = false ] = args; + const messageData = { action: kpActions.GET_DATABASE_STATUSES, keys: protocol.getKeys() @@ -255,7 +267,7 @@ protocol.getDatabaseStatuses = async function(tab, args = []) { try { const response = await protocolClient.sendMessage(tab, messageData, enableTimeout, triggerUnlock); if (response) { - keepass.databaseHash = response.hash; + keepass.databaseHash = response?.hash; // Return this error only if all databases are closed if (response?.statuses.every(s => s.locked)) { @@ -267,16 +279,10 @@ protocol.getDatabaseStatuses = async function(tab, args = []) { return response; } - // TODO: Check if these are even possible ..? - keepass.databaseHash = ''; keepass.isDatabaseClosed = true; - if (response.message && response.message === '') { - // ..? - keepass.isKeePassXCAvailable = false; - keepass.handleError(tab, kpErrors.TIMEOUT_OR_NOT_CONNECTED); - } else { - keepass.handleError(tab, response.errorCode, response.error); - } + keepass.isKeePassXCAvailable = false; + keepass.databaseHash = ''; + keepass.handleError(tab, kpErrors.TIMEOUT_OR_NOT_CONNECTED); } catch (err) { logError(`getDatabaseStatuses failed: ${err}`); } @@ -346,10 +352,9 @@ protocol.requestAutotype = async function(tab, args = []) { return false; } - const search = getTopLevelDomainFromUrl(args[0]); const messageData = { action: kpActions.REQUEST_AUTOTYPE, - search: search + search: getTopLevelDomainFromUrl(args[0]) }; try { @@ -364,6 +369,9 @@ protocol.requestAutotype = async function(tab, args = []) { protocol.testAssociationFromDatabaseStatuses = async function(tab, args = []) { const databaseStatuses = await protocol.getDatabaseStatuses(tab, args); console.log(databaseStatuses); + if (!databaseStatuses) { + return {}; + } const result = { areAllLocked: true, @@ -395,7 +403,6 @@ protocol.testAssociationFromDatabaseStatuses = async function(tab, args = []) { // But only if the current database is not locked.. if (!isCurrentAssociated && !isCurrentLocked) { console.log('Current one is not associated'); - } // This should be true only if all databases are locked @@ -417,6 +424,7 @@ protocol.updateCredentials = async function(tab, args = []) { const [ entryId, username, password, url, group, groupUuid ] = args; const [ dbid ] = keepass.getCryptoKey(); + const messageData = { action: kpActions.CREATE_CREDENTIALS, id: dbid, diff --git a/keepassxc-browser/background/protocolClient.js b/keepassxc-browser/background/protocolClient.js index 8c50362..23c5fb5 100644 --- a/keepassxc-browser/background/protocolClient.js +++ b/keepassxc-browser/background/protocolClient.js @@ -16,7 +16,7 @@ const protocolBuffer = { matchAndRemove(msg) { for (let i = 0; i < this.buffer.length; ++i) { if (msg?.requestID === this.buffer[i].requestID - || (msg.action === 'change-public-keys' && msg?.action === this.buffer[i].action)) { + || (msg.action === kpActions.CHANGE_PUBLIC_KEYS && msg?.action === this.buffer[i].action)) { this.buffer.splice(i, 1); return true; } @@ -43,7 +43,7 @@ protocolClient.sendNativeMessage = function(requestAction, request, enableTimeou const listener = ((port) => { const handler = (msg) => { - if (msg && (msg?.requestID === request.requestID || msg?.action === 'change-public-keys')) { + if (msg && (msg?.requestID === request.requestID || msg?.action === kpActions.CHANGE_PUBLIC_KEYS)) { // Only resolve a matching response if (protocolBuffer.matchAndRemove(msg)) { port.removeListener(handler); @@ -91,7 +91,7 @@ protocolClient.sendMessage = async function(tab, messageData, enableTimeout = fa const encryptedMessage = protocolClient.encrypt(messageData, nonce); const request = protocolClient.buildRequest(encryptedMessage, nonce, keepass.clientID, triggerUnlock); const response = await protocolClient.sendNativeMessage(messageData.action, request, enableTimeout); - const incrementedNonce = keepassClient.incrementedNonce(nonce); + const incrementedNonce = protocolClient.incrementedNonce(nonce); return protocolClient.handleResponse(response, incrementedNonce, tab); }; @@ -101,7 +101,7 @@ protocolClient.buildRequest = function(encryptedMessage, nonce, clientID, trigge message: encryptedMessage, nonce: nonce, clientID: clientID, - requestID: keepassClient.getRequestId() + requestID: protocolClient.getRequestId() }; if (triggerUnlock) { @@ -114,7 +114,7 @@ protocolClient.buildRequest = function(encryptedMessage, nonce, clientID, trigge // Verifies nonces, decrypts and parses the response protocolClient.handleResponse = function(response, incrementedNonce, tab) { if (response.message && protocolClient.verifyNonce(response, incrementedNonce)) { - const res = keepassClient.decrypt(response.message, response.nonce); + const res = protocolClient.decrypt(response.message, response.nonce); if (!res) { keepass.handleError(tab, kpErrors.CANNOT_DECRYPT_MESSAGE); return undefined; @@ -136,7 +136,7 @@ protocolClient.verifyNonce = function(response, nonce) { return false; } - if (!keepassClient.checkNonceLength(response.nonce)) { + if (!protocolClient.checkNonceLength(response.nonce)) { logError('Incorrect nonce length'); return false; } @@ -202,7 +202,7 @@ protocolClient.generateIdKey = function() { }; protocolClient.generateClientId = function() { - return nacl.util.encodeBase64(nacl.randomBytes(keepassClient.keySize)); + return nacl.util.encodeBase64(nacl.randomBytes(protocolClient.keySize)); }; //-------------------------------------------------------------------------- diff --git a/keepassxc-browser/popups/popup.js b/keepassxc-browser/popups/popup.js index c78bf6c..c176386 100644 --- a/keepassxc-browser/popups/popup.js +++ b/keepassxc-browser/popups/popup.js @@ -140,7 +140,7 @@ const sendMessageToTab = async function(message) { $('#reopen-database-button').addEventListener('click', async () => { statusResponse(await browser.runtime.sendMessage({ action: 'get_status', - args: [ false, true ] // Set forcePopup to true + args: [ false, true ] // Set triggerUnlock to true })); }); diff --git a/keepassxc-browser/popups/popup_login.js b/keepassxc-browser/popups/popup_login.js index b46c460..b063307 100644 --- a/keepassxc-browser/popups/popup_login.js +++ b/keepassxc-browser/popups/popup_login.js @@ -75,7 +75,7 @@ $('#reopen-database-button').addEventListener('click', (e) => { browser.runtime.sendMessage({ action: 'get_status', - args: [ false, true ] // Set forcePopup to true + args: [ false, true ] // Set triggerUnlock to true }); }); })();