mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-24 21:31:04 +00:00
Bug 1302288 - Implement PlacesSyncUtils.bookmarks.fetch
. r=markh
MozReview-Commit-ID: 2CcE8DxHott --HG-- extra : rebase_source : 7af66f06b889ca956cde0ff4499fcc6e74336e5c
This commit is contained in:
parent
25e23d96ea
commit
07d9b90407
@ -52,6 +52,26 @@ const MOBILE_ANNO = "MobileBookmarks";
|
||||
// the tracker doesn't currently distinguish between the two.
|
||||
const IGNORED_SOURCES = [SOURCE_SYNC, SOURCE_IMPORT, SOURCE_IMPORT_REPLACE];
|
||||
|
||||
// Returns the constructor for a bookmark record type.
|
||||
function getTypeObject(type) {
|
||||
switch (type) {
|
||||
case "bookmark":
|
||||
case "microsummary":
|
||||
return Bookmark;
|
||||
case "query":
|
||||
return BookmarkQuery;
|
||||
case "folder":
|
||||
return BookmarkFolder;
|
||||
case "livemark":
|
||||
return Livemark;
|
||||
case "separator":
|
||||
return BookmarkSeparator;
|
||||
case "item":
|
||||
return PlacesItem;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
this.PlacesItem = function PlacesItem(collection, id, type) {
|
||||
CryptoWrapper.call(this, collection, id);
|
||||
this.type = type || "item";
|
||||
@ -69,22 +89,11 @@ PlacesItem.prototype = {
|
||||
},
|
||||
|
||||
getTypeObject: function PlacesItem_getTypeObject(type) {
|
||||
switch (type) {
|
||||
case "bookmark":
|
||||
case "microsummary":
|
||||
return Bookmark;
|
||||
case "query":
|
||||
return BookmarkQuery;
|
||||
case "folder":
|
||||
return BookmarkFolder;
|
||||
case "livemark":
|
||||
return Livemark;
|
||||
case "separator":
|
||||
return BookmarkSeparator;
|
||||
case "item":
|
||||
return PlacesItem;
|
||||
let recordObj = getTypeObject(type);
|
||||
if (!recordObj) {
|
||||
throw new Error("Unknown places item object type: " + type);
|
||||
}
|
||||
throw "Unknown places item object type: " + type;
|
||||
return recordObj;
|
||||
},
|
||||
|
||||
__proto__: CryptoWrapper.prototype,
|
||||
@ -99,6 +108,13 @@ PlacesItem.prototype = {
|
||||
parentSyncId: this.parentid,
|
||||
};
|
||||
},
|
||||
|
||||
// Populates the record from a Sync bookmark object returned from
|
||||
// `PlacesSyncUtils.bookmarks.fetch`.
|
||||
fromSyncBookmark(item) {
|
||||
this.parentid = item.parentSyncId;
|
||||
this.parentName = item.parentTitle;
|
||||
},
|
||||
};
|
||||
|
||||
Utils.deferGetSet(PlacesItem,
|
||||
@ -122,6 +138,16 @@ Bookmark.prototype = {
|
||||
info.keyword = this.keyword;
|
||||
return info;
|
||||
},
|
||||
|
||||
fromSyncBookmark(item) {
|
||||
PlacesItem.prototype.fromSyncBookmark.call(this, item);
|
||||
this.title = item.title;
|
||||
this.bmkUri = item.url.href;
|
||||
this.description = item.description;
|
||||
this.loadInSidebar = item.loadInSidebar;
|
||||
this.tags = item.tags;
|
||||
this.keyword = item.keyword;
|
||||
},
|
||||
};
|
||||
|
||||
Utils.deferGetSet(Bookmark,
|
||||
@ -142,6 +168,12 @@ BookmarkQuery.prototype = {
|
||||
info.query = this.queryId;
|
||||
return info;
|
||||
},
|
||||
|
||||
fromSyncBookmark(item) {
|
||||
Bookmark.prototype.fromSyncBookmark.call(this, item);
|
||||
this.folderName = item.folder;
|
||||
this.queryId = item.query;
|
||||
},
|
||||
};
|
||||
|
||||
Utils.deferGetSet(BookmarkQuery,
|
||||
@ -161,6 +193,13 @@ BookmarkFolder.prototype = {
|
||||
info.title = this.title;
|
||||
return info;
|
||||
},
|
||||
|
||||
fromSyncBookmark(item) {
|
||||
PlacesItem.prototype.fromSyncBookmark.call(this, item);
|
||||
this.title = item.title;
|
||||
this.description = item.description;
|
||||
this.children = item.childSyncIds;
|
||||
},
|
||||
};
|
||||
|
||||
Utils.deferGetSet(BookmarkFolder, "cleartext", ["description", "title",
|
||||
@ -179,6 +218,14 @@ Livemark.prototype = {
|
||||
info.site = this.siteUri;
|
||||
return info;
|
||||
},
|
||||
|
||||
fromSyncBookmark(item) {
|
||||
BookmarkFolder.prototype.fromSyncBookmark.call(this, item);
|
||||
this.feedUri = item.feed.href;
|
||||
if (item.site) {
|
||||
this.siteUri = item.site.href;
|
||||
}
|
||||
},
|
||||
};
|
||||
|
||||
Utils.deferGetSet(Livemark, "cleartext", ["siteUri", "feedUri"]);
|
||||
@ -189,6 +236,11 @@ this.BookmarkSeparator = function BookmarkSeparator(collection, id) {
|
||||
BookmarkSeparator.prototype = {
|
||||
__proto__: PlacesItem.prototype,
|
||||
_logName: "Sync.Record.Separator",
|
||||
|
||||
fromSyncBookmark(item) {
|
||||
PlacesItem.prototype.fromSyncBookmark.call(this, item);
|
||||
this.pos = item.index;
|
||||
},
|
||||
};
|
||||
|
||||
Utils.deferGetSet(BookmarkSeparator, "cleartext", "pos");
|
||||
@ -716,121 +768,23 @@ BookmarksStore.prototype = {
|
||||
Async.promiseSpinningly(PlacesSyncUtils.bookmarks.changeGuid(oldID, newID));
|
||||
},
|
||||
|
||||
_getTags: function BStore__getTags(uri) {
|
||||
try {
|
||||
if (typeof(uri) == "string")
|
||||
uri = Utils.makeURI(uri);
|
||||
} catch(e) {
|
||||
this._log.warn("Could not parse URI \"" + uri + "\": " + e);
|
||||
}
|
||||
return PlacesUtils.tagging.getTagsForURI(uri, {});
|
||||
},
|
||||
|
||||
_getDescription: function BStore__getDescription(id) {
|
||||
try {
|
||||
return PlacesUtils.annotations.getItemAnnotation(id,
|
||||
PlacesSyncUtils.bookmarks.DESCRIPTION_ANNO);
|
||||
} catch (e) {
|
||||
return null;
|
||||
}
|
||||
},
|
||||
|
||||
_isLoadInSidebar: function BStore__isLoadInSidebar(id) {
|
||||
return PlacesUtils.annotations.itemHasAnnotation(id,
|
||||
PlacesSyncUtils.bookmarks.SIDEBAR_ANNO);
|
||||
},
|
||||
|
||||
// Create a record starting from the weave id (places guid)
|
||||
createRecord: function createRecord(id, collection) {
|
||||
let placeId = this.idForGUID(id);
|
||||
let record;
|
||||
if (placeId <= 0) { // deleted item
|
||||
record = new PlacesItem(collection, id);
|
||||
let item = Async.promiseSpinningly(PlacesSyncUtils.bookmarks.fetch(id));
|
||||
if (!item) { // deleted item
|
||||
let record = new PlacesItem(collection, id);
|
||||
record.deleted = true;
|
||||
return record;
|
||||
}
|
||||
|
||||
let parent = PlacesUtils.bookmarks.getFolderIdForItem(placeId);
|
||||
switch (PlacesUtils.bookmarks.getItemType(placeId)) {
|
||||
case PlacesUtils.bookmarks.TYPE_BOOKMARK:
|
||||
let bmkUri = PlacesUtils.bookmarks.getBookmarkURI(placeId).spec;
|
||||
if (bmkUri.indexOf("place:") == 0) {
|
||||
record = new BookmarkQuery(collection, id);
|
||||
|
||||
// Get the actual tag name instead of the local itemId
|
||||
let folder = bmkUri.match(/[:&]folder=(\d+)/);
|
||||
try {
|
||||
// There might not be the tag yet when creating on a new client
|
||||
if (folder != null) {
|
||||
folder = folder[1];
|
||||
record.folderName = PlacesUtils.bookmarks.getItemTitle(folder);
|
||||
this._log.trace("query id: " + folder + " = " + record.folderName);
|
||||
}
|
||||
}
|
||||
catch(ex) {}
|
||||
|
||||
// Persist the Smart Bookmark anno, if found.
|
||||
try {
|
||||
let anno = PlacesUtils.annotations.getItemAnnotation(placeId,
|
||||
PlacesSyncUtils.bookmarks.SMART_BOOKMARKS_ANNO);
|
||||
if (anno != null) {
|
||||
this._log.trace("query anno: " +
|
||||
PlacesSyncUtils.bookmarks.SMART_BOOKMARKS_ANNO +
|
||||
" = " + anno);
|
||||
record.queryId = anno;
|
||||
}
|
||||
}
|
||||
catch(ex) {}
|
||||
}
|
||||
else {
|
||||
record = new Bookmark(collection, id);
|
||||
}
|
||||
record.title = PlacesUtils.bookmarks.getItemTitle(placeId);
|
||||
|
||||
record.parentName = PlacesUtils.bookmarks.getItemTitle(parent);
|
||||
record.bmkUri = bmkUri;
|
||||
record.tags = this._getTags(record.bmkUri);
|
||||
record.keyword = PlacesUtils.bookmarks.getKeywordForBookmark(placeId);
|
||||
record.description = this._getDescription(placeId);
|
||||
record.loadInSidebar = this._isLoadInSidebar(placeId);
|
||||
break;
|
||||
|
||||
case PlacesUtils.bookmarks.TYPE_FOLDER:
|
||||
if (PlacesUtils.annotations
|
||||
.itemHasAnnotation(placeId, PlacesUtils.LMANNO_FEEDURI)) {
|
||||
record = new Livemark(collection, id);
|
||||
let as = PlacesUtils.annotations;
|
||||
record.feedUri = as.getItemAnnotation(placeId, PlacesUtils.LMANNO_FEEDURI);
|
||||
try {
|
||||
record.siteUri = as.getItemAnnotation(placeId, PlacesUtils.LMANNO_SITEURI);
|
||||
} catch (ex) {}
|
||||
} else {
|
||||
record = new BookmarkFolder(collection, id);
|
||||
}
|
||||
|
||||
if (parent > 0)
|
||||
record.parentName = PlacesUtils.bookmarks.getItemTitle(parent);
|
||||
record.title = PlacesUtils.bookmarks.getItemTitle(placeId);
|
||||
record.description = this._getDescription(placeId);
|
||||
record.children = Async.promiseSpinningly(
|
||||
PlacesSyncUtils.bookmarks.fetchChildSyncIds(id));
|
||||
break;
|
||||
|
||||
case PlacesUtils.bookmarks.TYPE_SEPARATOR:
|
||||
record = new BookmarkSeparator(collection, id);
|
||||
if (parent > 0)
|
||||
record.parentName = PlacesUtils.bookmarks.getItemTitle(parent);
|
||||
// Create a positioning identifier for the separator, used by _mapDupe
|
||||
record.pos = PlacesUtils.bookmarks.getItemIndex(placeId);
|
||||
break;
|
||||
|
||||
default:
|
||||
record = new PlacesItem(collection, id);
|
||||
this._log.warn("Unknown item type, cannot serialize: " +
|
||||
PlacesUtils.bookmarks.getItemType(placeId));
|
||||
let recordObj = getTypeObject(item.kind);
|
||||
if (!recordObj) {
|
||||
this._log.warn("Unknown item type, cannot serialize: " + item.kind);
|
||||
recordObj = PlacesItem;
|
||||
}
|
||||
let record = new recordObj(collection, id);
|
||||
record.fromSyncBookmark(item);
|
||||
|
||||
record.parentid = this.GUIDForId(parent);
|
||||
record.sortindex = this._calculateIndex(record);
|
||||
|
||||
return record;
|
||||
|
@ -264,6 +264,83 @@ const BookmarkSyncUtils = PlacesSyncUtils.bookmarks = Object.freeze({
|
||||
let insertInfo = validateNewBookmark(info);
|
||||
return insertSyncBookmark(insertInfo);
|
||||
}),
|
||||
|
||||
/**
|
||||
* Fetches a Sync bookmark object for an item in the tree. The object contains
|
||||
* the following properties, depending on the item's kind:
|
||||
*
|
||||
* - kind (all): A string representing the item's kind.
|
||||
* - syncId (all): The item's sync ID.
|
||||
* - parentSyncId (all): The sync ID of the item's parent.
|
||||
* - parentTitle (all): The title of the item's parent, used for de-duping.
|
||||
* Omitted for the Places root and parents with empty titles.
|
||||
* - title ("bookmark", "folder", "livemark", "query"): The item's title.
|
||||
* Omitted if empty.
|
||||
* - url ("bookmark", "query"): The item's URL.
|
||||
* - tags ("bookmark", "query"): An array containing the item's tags.
|
||||
* - keyword ("bookmark"): The bookmark's keyword, if one exists.
|
||||
* - description ("bookmark", "folder", "livemark"): The item's description.
|
||||
* Omitted if one isn't set.
|
||||
* - loadInSidebar ("bookmark", "query"): Whether to load the bookmark in
|
||||
* the sidebar. Always `false` for queries.
|
||||
* - feed ("livemark"): A `URL` object pointing to the livemark's feed URL.
|
||||
* - site ("livemark"): A `URL` object pointing to the livemark's site URL,
|
||||
* or `null` if one isn't set.
|
||||
* - childSyncIds ("folder"): An array containing the sync IDs of the item's
|
||||
* children, used to determine child order.
|
||||
* - folder ("query"): The tag folder name, if this is a tag query.
|
||||
* - query ("query"): The smart bookmark query name, if this is a smart
|
||||
* bookmark.
|
||||
* - index ("separator"): The separator's position within its parent.
|
||||
*/
|
||||
fetch: Task.async(function* (syncId) {
|
||||
let guid = BookmarkSyncUtils.syncIdToGuid(syncId);
|
||||
let bookmarkItem = yield PlacesUtils.bookmarks.fetch(guid);
|
||||
if (!bookmarkItem) {
|
||||
return null;
|
||||
}
|
||||
|
||||
// Convert the Places bookmark object to a Sync bookmark and add
|
||||
// kind-specific properties.
|
||||
let kind = yield getKindForItem(bookmarkItem);
|
||||
let item;
|
||||
switch (kind) {
|
||||
case BookmarkSyncUtils.KINDS.BOOKMARK:
|
||||
case BookmarkSyncUtils.KINDS.MICROSUMMARY:
|
||||
item = yield fetchBookmarkItem(bookmarkItem);
|
||||
break;
|
||||
|
||||
case BookmarkSyncUtils.KINDS.QUERY:
|
||||
item = yield fetchQueryItem(bookmarkItem);
|
||||
break;
|
||||
|
||||
case BookmarkSyncUtils.KINDS.FOLDER:
|
||||
item = yield fetchFolderItem(bookmarkItem);
|
||||
break;
|
||||
|
||||
case BookmarkSyncUtils.KINDS.LIVEMARK:
|
||||
item = yield fetchLivemarkItem(bookmarkItem);
|
||||
break;
|
||||
|
||||
case BookmarkSyncUtils.KINDS.SEPARATOR:
|
||||
item = yield placesBookmarkToSyncBookmark(bookmarkItem);
|
||||
item.index = bookmarkItem.index;
|
||||
break;
|
||||
|
||||
default:
|
||||
throw new Error(`Unknown bookmark kind: ${kind}`);
|
||||
}
|
||||
|
||||
// Sync uses the parent title for de-duping.
|
||||
if (bookmarkItem.parentGuid) {
|
||||
let parent = yield PlacesUtils.bookmarks.fetch(bookmarkItem.parentGuid);
|
||||
if ("title" in parent) {
|
||||
item.parentTitle = parent.title;
|
||||
}
|
||||
}
|
||||
|
||||
return item;
|
||||
}),
|
||||
});
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "BookmarkSyncLog", () => {
|
||||
@ -972,3 +1049,129 @@ function syncBookmarkToPlacesBookmark(info) {
|
||||
|
||||
return bookmarkInfo;
|
||||
}
|
||||
|
||||
// Creates and returns a Sync bookmark object containing the bookmark's
|
||||
// tags, keyword, description, and whether it loads in the sidebar.
|
||||
var fetchBookmarkItem = Task.async(function* (bookmarkItem) {
|
||||
let itemId = yield PlacesUtils.promiseItemId(bookmarkItem.guid);
|
||||
let item = yield placesBookmarkToSyncBookmark(bookmarkItem);
|
||||
|
||||
item.tags = PlacesUtils.tagging.getTagsForURI(
|
||||
PlacesUtils.toURI(bookmarkItem.url), {});
|
||||
|
||||
let keywordEntry = yield PlacesUtils.keywords.fetch({
|
||||
url: bookmarkItem.url,
|
||||
});
|
||||
if (keywordEntry) {
|
||||
item.keyword = keywordEntry.keyword;
|
||||
}
|
||||
|
||||
let description = getItemDescription(itemId);
|
||||
if (description) {
|
||||
item.description = description;
|
||||
}
|
||||
|
||||
item.loadInSidebar = PlacesUtils.annotations.itemHasAnnotation(itemId,
|
||||
BookmarkSyncUtils.SIDEBAR_ANNO);
|
||||
|
||||
return item;
|
||||
});
|
||||
|
||||
// Creates and returns a Sync bookmark object containing the folder's
|
||||
// description and children.
|
||||
var fetchFolderItem = Task.async(function* (bookmarkItem) {
|
||||
let itemId = yield PlacesUtils.promiseItemId(bookmarkItem.guid);
|
||||
let item = yield placesBookmarkToSyncBookmark(bookmarkItem);
|
||||
|
||||
let description = getItemDescription(itemId);
|
||||
if (description) {
|
||||
item.description = description;
|
||||
}
|
||||
|
||||
let db = yield PlacesUtils.promiseDBConnection();
|
||||
let children = yield fetchAllChildren(db, bookmarkItem.guid);
|
||||
item.childSyncIds = children.map(child =>
|
||||
BookmarkSyncUtils.guidToSyncId(child.guid)
|
||||
);
|
||||
|
||||
return item;
|
||||
});
|
||||
|
||||
// Creates and returns a Sync bookmark object containing the livemark's
|
||||
// description, children (none), feed URI, and site URI.
|
||||
var fetchLivemarkItem = Task.async(function* (bookmarkItem) {
|
||||
let itemId = yield PlacesUtils.promiseItemId(bookmarkItem.guid);
|
||||
let item = yield placesBookmarkToSyncBookmark(bookmarkItem);
|
||||
|
||||
let description = getItemDescription(itemId);
|
||||
if (description) {
|
||||
item.description = description;
|
||||
}
|
||||
|
||||
let feedAnno = PlacesUtils.annotations.getItemAnnotation(itemId,
|
||||
PlacesUtils.LMANNO_FEEDURI);
|
||||
item.feed = new URL(feedAnno);
|
||||
|
||||
let siteAnno = null;
|
||||
try {
|
||||
siteAnno = PlacesUtils.annotations.getItemAnnotation(itemId,
|
||||
PlacesUtils.LMANNO_SITEURI);
|
||||
} catch (ex) {}
|
||||
if (siteAnno != null) {
|
||||
item.site = new URL(siteAnno);
|
||||
}
|
||||
|
||||
return item;
|
||||
});
|
||||
|
||||
// Creates and returns a Sync bookmark object containing the query's tag
|
||||
// folder name and smart bookmark query ID.
|
||||
var fetchQueryItem = Task.async(function* (bookmarkItem) {
|
||||
let itemId = yield PlacesUtils.promiseItemId(bookmarkItem.guid);
|
||||
let item = yield placesBookmarkToSyncBookmark(bookmarkItem);
|
||||
|
||||
let description = getItemDescription(itemId);
|
||||
if (description) {
|
||||
item.description = description;
|
||||
}
|
||||
|
||||
let folder = null;
|
||||
let params = new URLSearchParams(bookmarkItem.url.pathname);
|
||||
let tagFolderId = +params.get("folder");
|
||||
if (tagFolderId) {
|
||||
try {
|
||||
let tagFolderGuid = yield PlacesUtils.promiseItemGuid(tagFolderId);
|
||||
let tagFolder = yield PlacesUtils.bookmarks.fetch(tagFolderGuid);
|
||||
folder = tagFolder.title;
|
||||
} catch (ex) {
|
||||
BookmarkSyncLog.warn("fetchQueryItem: Query " + bookmarkItem.url.href +
|
||||
" points to nonexistent folder " + tagFolderId, ex);
|
||||
}
|
||||
}
|
||||
if (folder != null) {
|
||||
item.folder = folder;
|
||||
}
|
||||
|
||||
let query = null;
|
||||
try {
|
||||
// Throws if the bookmark doesn't have the smart bookmark anno.
|
||||
query = PlacesUtils.annotations.getItemAnnotation(itemId,
|
||||
BookmarkSyncUtils.SMART_BOOKMARKS_ANNO);
|
||||
} catch (ex) {}
|
||||
if (query != null) {
|
||||
item.query = query;
|
||||
}
|
||||
|
||||
return item;
|
||||
});
|
||||
|
||||
// Returns an item's description, or `null` if one isn't set.
|
||||
function getItemDescription(id) {
|
||||
try {
|
||||
return PlacesUtils.annotations.getItemAnnotation(id,
|
||||
BookmarkSyncUtils.DESCRIPTION_ANNO);
|
||||
} catch (ex) {}
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
|
@ -343,13 +343,10 @@ add_task(function* test_update_annos() {
|
||||
let guids = yield populateTree(PlacesUtils.bookmarks.menuGuid, {
|
||||
kind: "folder",
|
||||
title: "folder",
|
||||
description: "Folder description",
|
||||
}, {
|
||||
kind: "bookmark",
|
||||
title: "bmk",
|
||||
url: "https://example.com",
|
||||
description: "Bookmark description",
|
||||
loadInSidebar: true,
|
||||
});
|
||||
|
||||
do_print("Add folder description");
|
||||
@ -1004,3 +1001,145 @@ add_task(function* test_insert_orphans() {
|
||||
|
||||
yield PlacesUtils.bookmarks.eraseEverything();
|
||||
});
|
||||
|
||||
add_task(function* test_fetch() {
|
||||
let folder = yield PlacesSyncUtils.bookmarks.insert({
|
||||
syncId: makeGuid(),
|
||||
parentSyncId: "menu",
|
||||
kind: "folder",
|
||||
description: "Folder description",
|
||||
});
|
||||
let bmk = yield PlacesSyncUtils.bookmarks.insert({
|
||||
syncId: makeGuid(),
|
||||
parentSyncId: "menu",
|
||||
kind: "bookmark",
|
||||
url: "https://example.com",
|
||||
description: "Bookmark description",
|
||||
loadInSidebar: true,
|
||||
tags: ["taggy"],
|
||||
});
|
||||
let folderBmk = yield PlacesSyncUtils.bookmarks.insert({
|
||||
syncId: makeGuid(),
|
||||
parentSyncId: folder.syncId,
|
||||
kind: "bookmark",
|
||||
url: "https://example.org",
|
||||
keyword: "kw",
|
||||
});
|
||||
let folderSep = yield PlacesSyncUtils.bookmarks.insert({
|
||||
syncId: makeGuid(),
|
||||
parentSyncId: folder.syncId,
|
||||
kind: "separator",
|
||||
});
|
||||
let tagQuery = yield PlacesSyncUtils.bookmarks.insert({
|
||||
kind: "query",
|
||||
syncId: makeGuid(),
|
||||
parentSyncId: "toolbar",
|
||||
url: "place:type=7&folder=90",
|
||||
folder: "taggy",
|
||||
title: "Tagged stuff",
|
||||
});
|
||||
let [, tagFolderId] = /\bfolder=(\d+)\b/.exec(tagQuery.url.pathname);
|
||||
let smartBmk = yield PlacesSyncUtils.bookmarks.insert({
|
||||
kind: "query",
|
||||
syncId: makeGuid(),
|
||||
parentSyncId: "toolbar",
|
||||
url: "place:folder=TOOLBAR",
|
||||
query: "BookmarksToolbar",
|
||||
title: "Bookmarks toolbar query",
|
||||
});
|
||||
|
||||
do_print("Fetch empty folder with description");
|
||||
{
|
||||
let item = yield PlacesSyncUtils.bookmarks.fetch(folder.syncId);
|
||||
deepEqual(item, {
|
||||
syncId: folder.syncId,
|
||||
kind: "folder",
|
||||
parentSyncId: "menu",
|
||||
description: "Folder description",
|
||||
childSyncIds: [folderBmk.syncId, folderSep.syncId],
|
||||
parentTitle: "Bookmarks Menu",
|
||||
}, "Should include description, children, and parent title in folder");
|
||||
}
|
||||
|
||||
do_print("Fetch bookmark with description, sidebar anno, and tags");
|
||||
{
|
||||
let item = yield PlacesSyncUtils.bookmarks.fetch(bmk.syncId);
|
||||
deepEqual(Object.keys(item).sort(), ["syncId", "kind", "parentSyncId", "url",
|
||||
"tags", "description", "loadInSidebar", "parentTitle"].sort(),
|
||||
"Should include bookmark-specific properties");
|
||||
equal(item.syncId, bmk.syncId, "Sync ID should match");
|
||||
equal(item.url.href, "https://example.com/", "Should return URL");
|
||||
equal(item.parentSyncId, "menu", "Should return parent sync ID");
|
||||
deepEqual(item.tags, ["taggy"], "Should return tags");
|
||||
equal(item.description, "Bookmark description", "Should return bookmark description");
|
||||
strictEqual(item.loadInSidebar, true, "Should return sidebar anno");
|
||||
equal(item.parentTitle, "Bookmarks Menu", "Should return parent title");
|
||||
}
|
||||
|
||||
do_print("Fetch bookmark with keyword; without parent title or annos");
|
||||
{
|
||||
let item = yield PlacesSyncUtils.bookmarks.fetch(folderBmk.syncId);
|
||||
deepEqual(Object.keys(item).sort(), ["syncId", "kind", "parentSyncId",
|
||||
"url", "keyword", "tags", "loadInSidebar"].sort(),
|
||||
"Should omit blank bookmark-specific properties");
|
||||
strictEqual(item.loadInSidebar, false, "Should not load bookmark in sidebar");
|
||||
deepEqual(item.tags, [], "Tags should be empty");
|
||||
equal(item.keyword, "kw", "Should return keyword");
|
||||
}
|
||||
|
||||
do_print("Fetch separator");
|
||||
{
|
||||
let item = yield PlacesSyncUtils.bookmarks.fetch(folderSep.syncId);
|
||||
strictEqual(item.index, 1, "Should return separator position");
|
||||
}
|
||||
|
||||
do_print("Fetch tag query");
|
||||
{
|
||||
let item = yield PlacesSyncUtils.bookmarks.fetch(tagQuery.syncId);
|
||||
deepEqual(Object.keys(item).sort(), ["syncId", "kind", "parentSyncId",
|
||||
"url", "title", "folder", "parentTitle"].sort(),
|
||||
"Should include query-specific properties");
|
||||
equal(item.url.href, `place:type=7&folder=${tagFolderId}`, "Should not rewrite outgoing tag queries");
|
||||
equal(item.folder, "taggy", "Should return tag name for tag queries");
|
||||
}
|
||||
|
||||
do_print("Fetch smart bookmark");
|
||||
{
|
||||
let item = yield PlacesSyncUtils.bookmarks.fetch(smartBmk.syncId);
|
||||
deepEqual(Object.keys(item).sort(), ["syncId", "kind", "parentSyncId",
|
||||
"url", "title", "query", "parentTitle"].sort(),
|
||||
"Should include smart bookmark-specific properties");
|
||||
equal(item.query, "BookmarksToolbar", "Should return query name for smart bookmarks");
|
||||
}
|
||||
|
||||
yield PlacesUtils.bookmarks.eraseEverything();
|
||||
});
|
||||
|
||||
add_task(function* test_fetch_livemark() {
|
||||
let { server, site, stopServer } = makeLivemarkServer();
|
||||
|
||||
try {
|
||||
do_print("Create livemark");
|
||||
let livemark = yield PlacesUtils.livemarks.addLivemark({
|
||||
parentGuid: PlacesUtils.bookmarks.menuGuid,
|
||||
feedURI: uri(site + "/feed/1"),
|
||||
siteURI: uri(site),
|
||||
index: PlacesUtils.bookmarks.DEFAULT_INDEX,
|
||||
});
|
||||
PlacesUtils.annotations.setItemAnnotation(livemark.id, DESCRIPTION_ANNO,
|
||||
"Livemark description", 0, PlacesUtils.annotations.EXPIRE_NEVER);
|
||||
|
||||
do_print("Fetch livemark");
|
||||
let item = yield PlacesSyncUtils.bookmarks.fetch(livemark.guid);
|
||||
deepEqual(Object.keys(item).sort(), ["syncId", "kind", "parentSyncId",
|
||||
"description", "feed", "site", "parentTitle"].sort(),
|
||||
"Should include livemark-specific properties");
|
||||
equal(item.description, "Livemark description", "Should return description");
|
||||
equal(item.feed.href, site + "/feed/1", "Should return feed URL");
|
||||
equal(item.site.href, site + "/", "Should return site URL");
|
||||
} finally {
|
||||
yield stopServer();
|
||||
}
|
||||
|
||||
yield PlacesUtils.bookmarks.eraseEverything();
|
||||
});
|
||||
|
Loading…
Reference in New Issue
Block a user