Skip to content
This repository has been archived by the owner on Dec 11, 2019. It is now read-only.

Add Importer support #4049

Merged
merged 1 commit into from
Sep 21, 2016
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 14 additions & 0 deletions app/aboutDialog.js
Original file line number Diff line number Diff line change
Expand Up @@ -25,3 +25,17 @@ ${locale.translation('licenseText')}`,
})
}, 50)
}

module.exports.showImportWarning = function () {
// The timeout is in case there's a call just after the modal to hide the menu.
// showMessageBox is a modal and blocks everything otherwise, so menu would remain open
// while the dialog is displayed.
setTimeout(() => {
dialog.showMessageBox({
title: 'Brave',
message: `${locale.translation('closeFirefoxWarning')}`,
icon: path.join(__dirname, '..', 'app', 'extensions', 'brave', 'img', 'braveAbout.png'),
buttons: ['Ok']
})
}, 50)
}
20 changes: 5 additions & 15 deletions app/browser/menu.js
Original file line number Diff line number Diff line change
Expand Up @@ -62,18 +62,6 @@ const createFileSubmenu = () => {
}
},
CommonMenu.separatorMenuItem,
/*
{
label: locale.translation('importFrom'),
visible: false
submenu: [
{label: 'Google Chrome...'},
{label: 'Firefox...'},
{label: 'Safari...'}
]
},
CommonMenu.separatorMenuItem,
*/
{
// this should be disabled when
// no windows are active
Expand Down Expand Up @@ -391,9 +379,7 @@ const createBookmarksSubmenu = () => {
},
CommonMenu.separatorMenuItem,
CommonMenu.bookmarksManagerMenuItem(),
CommonMenu.bookmarksToolbarMenuItem(),
CommonMenu.separatorMenuItem,
CommonMenu.importBookmarksMenuItem()
CommonMenu.bookmarksToolbarMenuItem()
]
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

there is some commented out code here in the menu.js that I think you can delete, now that you've added import functionality. Search for locale.translation('importFrom')


const bookmarks = menuUtil.createBookmarkMenuItems(appStore.getState().get('sites'))
Expand Down Expand Up @@ -473,6 +459,8 @@ const createHelpSubmenu = () => {
submenu.push(CommonMenu.separatorMenuItem)
submenu.push(CommonMenu.checkForUpdateMenuItem())
submenu.push(CommonMenu.separatorMenuItem)
submenu.push(CommonMenu.importBrowserDataMenuItem())
submenu.push(CommonMenu.separatorMenuItem)
submenu.push(CommonMenu.aboutBraveMenuItem())
}

Expand Down Expand Up @@ -555,6 +543,8 @@ const createMenu = () => {
CommonMenu.separatorMenuItem,
CommonMenu.checkForUpdateMenuItem(),
CommonMenu.separatorMenuItem,
CommonMenu.importBrowserDataMenuItem(),
CommonMenu.separatorMenuItem,
CommonMenu.preferencesMenuItem(),
CommonMenu.separatorMenuItem,
{
Expand Down
24 changes: 5 additions & 19 deletions app/common/commonMenu.js
Original file line number Diff line number Diff line change
Expand Up @@ -243,31 +243,17 @@ module.exports.passwordsMenuItem = () => {
}
}

module.exports.importBookmarksMenuItem = () => {
module.exports.importBrowserDataMenuItem = () => {
return {
label: locale.translation('importBookmarks'),
label: locale.translation('importBrowserData'),
click: function (item, focusedWindow) {
if (BrowserWindow.getAllWindows().length === 0) {
appActions.newWindow(undefined, undefined, undefined, function () {
// The timeout here isn't necessary but giving the window a bit of time to popup
// before the modal file picker pops up seems to work nicer.
setTimeout(() =>
module.exports.sendToFocusedWindow(BrowserWindow.getAllWindows()[0], [messages.IMPORT_BOOKMARKS]), 100)
})
return
if (process.type === 'browser') {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

process.emit(messages.IMPORT_BROWSER_DATA_NOW)
} else {
setTimeout(() =>
module.exports.sendToFocusedWindow(BrowserWindow.getAllWindows()[0], [messages.IMPORT_BOOKMARKS]), 100)
electron.ipcRenderer.send(messages.IMPORT_BROWSER_DATA_NOW)
}
}
}
/*
submenu: [
{label: 'Google Chrome...'},
{label: 'Firefox...'},
{label: 'Safari...'}
]
*/
}

module.exports.reportAnIssueMenuItem = () => {
Expand Down
8 changes: 8 additions & 0 deletions app/extensions/brave/locales/en-US/app.properties
Original file line number Diff line number Diff line change
Expand Up @@ -206,3 +206,11 @@ windowCaptionButtonMinimize=Minimize
windowCaptionButtonMaximize=Maximize
windowCaptionButtonRestore=Restore Down
windowCaptionButtonClose=Close
importBrowserData=Import browser data
import=Import
importDataWarning=Note: Each browser has a different set of importable data.
importDataCloseBrowserWarning=Please make sure the selected browser is closed before importing your data.
closeFirefoxWarning=Firefox must be closed during data import. Please close and try again.
favoritesOrBookmarks=Favorites/Bookmarks
mergeIntoBookmarksToolbar=Merge Favorites into Bookmarks Toolbar
cookies=Cookies
2 changes: 1 addition & 1 deletion app/extensions/brave/locales/en-US/menu.properties
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ checkForUpdates=Check for Updates…
preferences=Preferences…
settings=Settings…
bookmarksManager=Bookmarks Manager…
importBookmarks=Import Bookmarks (from HTML export)
importBrowserData=Import Browser Data
reportAnIssue=Report an Issue
submitFeedback=Submit Feedback…
bookmarksToolbar=Bookmarks Toolbar
Expand Down
2 changes: 2 additions & 0 deletions app/extensions/brave/locales/en-US/preferences.properties
Original file line number Diff line number Diff line change
Expand Up @@ -216,3 +216,5 @@ clearBrowsingDataNow=Clear Browsing Data Now…
autofillSettings=Autofill Settings
manageAutofillData=Manage Autofill Data…
enableAutofill=Enable Autofill
importBrowserData=Import Browser Data
importNow=Import now…
181 changes: 181 additions & 0 deletions app/importer.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,181 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/. */

'strict mode'

const electron = require('electron')
const importer = electron.importer
const dialog = electron.dialog
const BrowserWindow = electron.BrowserWindow
const session = electron.session
const Immutable = require('immutable')
const showImportWarning = require('./aboutDialog').showImportWarning
const siteUtil = require('../js/state/siteUtil')
const AppStore = require('../js/stores/appStore')
const siteTags = require('../js/constants/siteTags')
const appActions = require('../js/actions/appActions')
const messages = require('../js/constants/messages')

var isMergeFavorites = false

exports.init = () => {
importer.initialize()
}

exports.importData = (selected) => {
if (selected.get('mergeFavorites')) {
isMergeFavorites = true
}
if (selected !== undefined) {
importer.importData(selected.toJS())
}
}

exports.importHTML = (selected) => {
if (selected.get('mergeFavorites')) {
isMergeFavorites = true
}
const files = dialog.showOpenDialog({
properties: ['openFile'],
filters: [{
name: 'HTML',
extensions: ['html', 'htm']
}]
})
if (files && files.length > 0) {
const file = files[0]
importer.importHTML(file)
}
}

importer.on('update-supported-browsers', (e, detail) => {
isMergeFavorites = false
if (BrowserWindow.getFocusedWindow()) {
BrowserWindow.getFocusedWindow().webContents.send(messages.IMPORTER_LIST, detail)
}
})

importer.on('show-warning-dialog', (e) => {
})

importer.on('add-password-form', (e, detail) => {
})

importer.on('add-history-page', (e, history, visitSource) => {
let sites = []
for (let i = 0; i < history.length; ++i) {
const site = {
title: history[i].title,
location: history[i].url,
lastAccessedTime: history[i].last_visit * 1000
}
sites.push(site)
}
appActions.addSite(Immutable.fromJS(sites))
})

importer.on('add-homepage', (e, detail) => {
})

importer.on('add-bookmarks', (e, bookmarks, topLevelFolder) => {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this handler has a LOT going on in it... Any chance we could break this (or parts of it) out into a method? Looks generic enough (not dependent on electron) to put into a utils class, which means we could eventually unit test it too 😄

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

But the handler is for electron dependent bookmarks object and whole block is meant to handle it specifically. So I am not sure that we can pull out a generic method from it.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ah- makes sense. I'm OK w/ it as-is 😄

let nextFolderId = siteUtil.getNextFolderId(AppStore.getState().get('sites'))
let pathMap = {}
let sites = []
let topLevelFolderId = 0
if (!isMergeFavorites) {
topLevelFolderId = nextFolderId++
sites.push({
title: topLevelFolder,
folderId: topLevelFolderId,
parentFolderId: 0,
lastAccessedTime: (new Date()).getTime(),
tags: [siteTags.BOOKMARK_FOLDER]
})
} else {
// Merge into existing bookmark toolbar
pathMap[topLevelFolder] = topLevelFolderId
pathMap['Bookmarks Toolbar'] = 0 // Firefox
pathMap['Bookmarks Bar'] = 0 // Chrome on mac
pathMap['Other Bookmarks'] = -1 // Chrome on mac
pathMap['Bookmarks bar'] = 0 // Chrome on win/linux
pathMap['Other bookmarks'] = -1 // Chrome on win/linux
pathMap['Bookmark Bar'] = 0 // Safari
pathMap['Links'] = 0 // Edge, IE
}
for (let i = 0; i < bookmarks.length; ++i) {
const pathLen = bookmarks[i].path.length
let parentFolderId = topLevelFolderId
if (pathLen) {
const parentFolder = bookmarks[i].path[pathLen - 1]
parentFolderId = pathMap[parentFolder]
if (parentFolderId === undefined) {
parentFolderId = nextFolderId++
pathMap[parentFolder] = parentFolderId
const folder = {
title: parentFolder,
folderId: parentFolderId,
parentFolderId: pathMap[bookmarks[i].path[pathLen - 2]] === undefined ? topLevelFolderId : pathMap[bookmarks[i].path[pathLen - 2]],
lastAccessedTime: (new Date()).getTime(),
tags: [siteTags.BOOKMARK_FOLDER]
}
sites.push(folder)
}
}
if (bookmarks[i].is_folder) {
const folderId = nextFolderId++
pathMap[bookmarks[i].title] = folderId
const folder = {
title: bookmarks[i].title,
folderId: folderId,
parentFolderId: parentFolderId,
lastAccessedTime: bookmarks[i].creation_time * 1000,
tags: [siteTags.BOOKMARK_FOLDER]
}
sites.push(folder)
} else {
const site = {
title: bookmarks[i].title,
location: bookmarks[i].url,
parentFolderId: parentFolderId,
lastAccessedTime: bookmarks[i].creation_time * 1000,
tags: [siteTags.BOOKMARK]
}
sites.push(site)
}
}
appActions.addSite(Immutable.fromJS(sites))
})

importer.on('add-favicons', (e, detail) => {
})

importer.on('add-keywords', (e, templateUrls, uniqueOnHostAndPath) => {
})

importer.on('add-autofill-form-data-entries', (e, detail) => {
})

importer.on('add-cookies', (e, cookies) => {
for (let i = 0; i < cookies.length; ++i) {
const cookie = {
url: cookies[i].url,
name: cookies[i].name,
value: cookies[i].value,
domain: cookies[i].domain,
path: cookies[i].path,
secure: cookies[i].secure,
httpOnly: cookies[i].httponly,
expirationDate: cookies[i].expiry_date
}
session.defaultSession.cookies.set(cookie, (error) => {
if (error) {
console.error(error)
}
})
}
})

importer.on('show-warning-dialog', (e) => {
showImportWarning()
})
10 changes: 10 additions & 0 deletions app/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ const ipcMain = electron.ipcMain
const Immutable = require('immutable')
const Menu = require('./browser/menu')
const Updater = require('./updater')
const Importer = require('./importer')
const messages = require('../js/constants/messages')
const appConfig = require('../js/constants/appConfig')
const appActions = require('../js/actions/appActions')
Expand Down Expand Up @@ -686,6 +687,10 @@ app.on('ready', () => {
}
})

ipcMain.on(messages.IMPORT_BROWSER_DATA_NOW, () => {
Importer.init()
})

// Setup the crash handling
CrashHerald.init()

Expand All @@ -709,6 +714,11 @@ app.on('ready', () => {
process.on(messages.UPDATE_META_DATA_RETRIEVED, (metadata) => {
console.log(metadata)
})

// This is fired by a menu entry
process.on(messages.IMPORT_BROWSER_DATA_NOW, () => {
Importer.init()
})
})
})
})
5 changes: 3 additions & 2 deletions app/locale.js
Original file line number Diff line number Diff line change
Expand Up @@ -145,7 +145,7 @@ var rendererIdentifiers = function () {
'preferences',
'settings',
'bookmarksManager',
'importBookmarks',
'importBrowserData',
'reportAnIssue',
'submitFeedback',
'bookmarksToolbar',
Expand Down Expand Up @@ -212,7 +212,8 @@ var rendererIdentifiers = function () {
'windowCaptionButtonMinimize',
'windowCaptionButtonMaximize',
'windowCaptionButtonRestore',
'windowCaptionButtonClose'
'windowCaptionButtonClose',
'closeFirefoxWarning'
]
}

Expand Down
Loading