/* 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/. */ 'use strict'; module.metadata = { 'stability': 'experimental', 'engines': { 'Palemoon': '*', 'Firefox': '*', "SeaMonkey": '*' } }; const { Cc, Ci } = require('chrome'); const { Unknown } = require('../platform/xpcom'); const { Class } = require('../core/heritage'); const { merge } = require('../util/object'); const bookmarkService = Cc['@mozilla.org/browser/nav-bookmarks-service;1'] .getService(Ci.nsINavBookmarksService); const historyService = Cc['@mozilla.org/browser/nav-history-service;1'] .getService(Ci.nsINavHistoryService); const { mapBookmarkItemType } = require('./utils'); const { EventTarget } = require('../event/target'); const { emit } = require('../event/core'); const { when } = require('../system/unload'); const emitter = EventTarget(); var HISTORY_ARGS = { onBeginUpdateBatch: [], onEndUpdateBatch: [], onClearHistory: [], onDeleteURI: ['url'], onDeleteVisits: ['url', 'visitTime'], onPageChanged: ['url', 'property', 'value'], onTitleChanged: ['url', 'title'], onVisit: [ 'url', 'visitId', 'time', 'sessionId', 'referringId', 'transitionType' ] }; var HISTORY_EVENTS = { onBeginUpdateBatch: 'history-start-batch', onEndUpdateBatch: 'history-end-batch', onClearHistory: 'history-start-clear', onDeleteURI: 'history-delete-url', onDeleteVisits: 'history-delete-visits', onPageChanged: 'history-page-changed', onTitleChanged: 'history-title-changed', onVisit: 'history-visit' }; var BOOKMARK_ARGS = { onItemAdded: [ 'id', 'parentId', 'index', 'type', 'url', 'title', 'dateAdded' ], onItemChanged: [ 'id', 'property', null, 'value', 'lastModified', 'type', 'parentId' ], onItemMoved: [ 'id', 'previousParentId', 'previousIndex', 'currentParentId', 'currentIndex', 'type' ], onItemRemoved: ['id', 'parentId', 'index', 'type', 'url'], onItemVisited: ['id', 'visitId', 'time', 'transitionType', 'url', 'parentId'] }; var BOOKMARK_EVENTS = { onItemAdded: 'bookmark-item-added', onItemChanged: 'bookmark-item-changed', onItemMoved: 'bookmark-item-moved', onItemRemoved: 'bookmark-item-removed', onItemVisited: 'bookmark-item-visited', }; function createHandler (type, propNames) { propNames = propNames || []; return function (...args) { let data = propNames.reduce((acc, prop, i) => { if (prop) acc[prop] = formatValue(prop, args[i]); return acc; }, {}); emit(emitter, 'data', { type: type, data: data }); }; } /* * Creates an observer, creating handlers based off of * the `events` names, and ordering arguments from `propNames` hash */ function createObserverInstance (events, propNames) { let definition = Object.keys(events).reduce((prototype, eventName) => { prototype[eventName] = createHandler(events[eventName], propNames[eventName]); return prototype; }, {}); return Class(merge(definition, { extends: Unknown }))(); } /* * Formats `data` based off of the value of `type` */ function formatValue (type, data) { if (type === 'type') return mapBookmarkItemType(data); if (type === 'url' && data) return data.spec; return data; } var historyObserver = createObserverInstance(HISTORY_EVENTS, HISTORY_ARGS); historyService.addObserver(historyObserver, false); var bookmarkObserver = createObserverInstance(BOOKMARK_EVENTS, BOOKMARK_ARGS); bookmarkService.addObserver(bookmarkObserver, false); when(() => { historyService.removeObserver(historyObserver); bookmarkService.removeObserver(bookmarkObserver); }); exports.events = emitter;