www

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs | Submodules | README | LICENSE

commit 21cd15b0680617d92624d140fc9e0cd39169ce11
parent 7445f81042f90448b64a6b9c4ac67856078ab4e6
Author: Aurimas Vinckevicius <aurimas.dev@gmail.com>
Date:   Tue, 10 Mar 2015 19:46:48 -0500

Port Zotero.Item.toJSON from api_syncing branch
* Modified to use synchronous DB access
* Take patchBase argument as an option
* Update to conform to v3 API

Diffstat:
Mchrome/content/zotero/xpcom/data/item.js | 186+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 186 insertions(+), 0 deletions(-)

diff --git a/chrome/content/zotero/xpcom/data/item.js b/chrome/content/zotero/xpcom/data/item.js @@ -4918,6 +4918,192 @@ Zotero.Item.prototype.serialize = function(mode) { return arr; } +/** + * Serializes Zotero Item into Zotero web server API JSON format + * + * @param {Object} options + * mode {String}: [new|full|patch] "new" is default. "full" mode includes all + * fields even if empty. "patch" returns only fields that are different from + * those in patchBase + * patchBase {Object}: Item in API JSON format to be compared to in + * "patch" mode. Required if "patch" mode is specified + */ +Zotero.Item.prototype.toJSON = function(options) { + if (this.id || this.key) { + if (!this._primaryDataLoaded) { + this.loadPrimaryData(true); + } + + if (this.id) { + if (!this._itemDataLoaded) this._loadItemData(); + if (this.isRegularItem() && !this._creatorsLoaded) this._loadCreators(); + if (!this._relatedItemsLoaded) this._loadRelatedItems(); + } + } + + if (this.hasChanged()) { + throw new Error("Cannot generate JSON from changed item"); + } + + options = options || {}; + let mode = options.mode || 'new'; + let patchBase = options.patchBase; + + if (mode == 'patch') { + if (!patchBase) { + throw new Error('Cannot use "patch" mode if patchBase not provided'); + } + } + else if (patchBase) { + Zotero.debug('Zotero.Item.toJSON: ignoring provided patchBase in "' + mode + '" mode', 2); + } + + let obj = { + key: this.key || false, + version: 1, + itemType: Zotero.ItemTypes.getName(this.itemTypeID), + tags: [], + collections: [], + relations: {} + }; + + // Type-specific fields + for (let i in this._itemData) { + let val = '' + this.getField(i); + if (val !== '' || mode == 'full') { + let name = Zotero.ItemFields.getName(i); + if (name == 'version') { + // Changed in API v3 to avoid clash with 'version' above + // Remove this after https://github.com/zotero/zotero/issues/670 + name = 'versionNumber'; + } + + obj[name] = val; + } + } + + if (this.isRegularItem()) { + // Creators + obj.creators = []; + let creators = this.getCreators(); + for (let i=0; i<creators.length; i++) { + let creator = creators[i].ref; + let creatorObj = { + creatorType: Zotero.CreatorTypes.getName(creators[i].creatorTypeID) + }; + + if (creator.fieldMode == 1) { + creatorObj.name = creator.lastName; + } else { + creatorObj.lastName = creator.lastName; + creatorObj.firstName = creator.firstName; + } + + obj.creators.push(creatorObj); + } + } + else { + // Notes or Attachments + let parent = this.getSourceKey(); + if (parent || mode == 'full') { + obj.parentItem = parent ? parent : false; + } + + // Notes and embedded attachment notes + let note = this.getNote(); + if (note !== "" || mode == 'full') { + obj.note = note; + } + } + + // Attachment fields + if (this.isAttachment()) { + obj.linkMode = ['imported_file','imported_url','linked_file','linked_url'][this.attachmentLinkMode]; + obj.contentType = this.attachmentMIMEType; + obj.charset = this.attachmentCharset; + obj.path = this.attachmentPath; + } + + // Tags + let tags = this.getTags(); + for (let i=0; i<tags.length; i++) { + let tag = { + tag: tags[i].name + }; + if (tags[i].type) tag.type = tags[i].type + + obj.tags.push(tag); + } + + // Collections + if (this.id) { + let collections = this.getCollections(); + for (let i=0; i<collections.length; i++) { + let collection = Zotero.Collections.get(collections[i]); + obj.collections.push(collection.key); + } + } + + // Relations + if (this.key) { + // Relations other than through the "Related" tab + let itemURI = Zotero.URI.getItemURI(this), + rels = Zotero.Relations.getByURIs(itemURI); + for (let i=0; i<rels.length; i++) { + let rel = rels[i].load(); + obj.relations[rel.predicate] = rel.object; + } + + // Related items (in both directions) + let relatedItems = this._getRelatedItemsBidirectional(); + let pred = 'dc:relation'; + for (let i=0; i<relatedItems.length; i++) { + let item = Zotero.Items.get(relatedItems[i]); + let uri = Zotero.URI.getItemURI(item); + if (obj.relations[pred]) { + if (typeof obj.relations[pred] == 'string') { + obj.relations[pred] = [uri]; + } + obj.relations[pred].push(uri) + } + else { + obj.relations[pred] = uri; + } + } + } + + // Deleted + let deleted = this.deleted; + if (deleted || mode == 'full') { + obj.deleted = deleted; + } + + obj.dateAdded = Zotero.Date.sqlToISO8601(this.dateAdded); + obj.dateModified = Zotero.Date.sqlToISO8601(this.dateModified); + + if (mode == 'patch') { + // For "patch" mode, remove fields that have the same values + for (let i in patchBase) { + switch (i) { + case 'itemKey': + case 'itemVersion': + case 'dateModified': + continue; + } + + if (i in obj) { + if (obj[i] === patchBase[i]) { + delete obj[i]; + } + } + else { + obj[i] = ""; + } + } + } + + return obj; +}; //////////////////////////////////////////////////////////////////////////////