Save createdByUserID and lastModifiedByUserID for group items
This commit is contained in:
		
					parent
					
						
							
								bb0a1dab13
							
						
					
				
			
			
				commit
				
					
						b54d4e78b7
					
				
			
		
					 9 changed files with 317 additions and 40 deletions
				
			
		| 
						 | 
				
			
			@ -38,6 +38,8 @@ Zotero.Item = function(itemTypeOrID) {
 | 
			
		|||
	
 | 
			
		||||
	// loadPrimaryData (additional properties in dataObject.js)
 | 
			
		||||
	this._itemTypeID = null;
 | 
			
		||||
	this._createdByUserID = null;
 | 
			
		||||
	this._lastModifiedByUserID = null;
 | 
			
		||||
	this._firstCreator = null;
 | 
			
		||||
	this._sortCreator = null;
 | 
			
		||||
	this._attachmentCharset = null;
 | 
			
		||||
| 
						 | 
				
			
			@ -107,33 +109,19 @@ Zotero.defineProperty(Zotero.Item.prototype, 'itemID', {
 | 
			
		|||
	},
 | 
			
		||||
	enumerable: false
 | 
			
		||||
});
 | 
			
		||||
Zotero.defineProperty(Zotero.Item.prototype, 'libraryID', {
 | 
			
		||||
	get: function() { return this._libraryID; },
 | 
			
		||||
	set: function(val) { return this.setField('libraryID', val); }
 | 
			
		||||
});
 | 
			
		||||
Zotero.defineProperty(Zotero.Item.prototype, 'key', {
 | 
			
		||||
	get: function() { return this._key; },
 | 
			
		||||
	set: function(val) { return this.setField('key', val); }
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
for (let name of ['libraryID', 'key', 'dateAdded', 'dateModified', 'version', 'synced',
 | 
			
		||||
		'createdByUserID', 'lastModifiedByUserID']) {
 | 
			
		||||
	let prop = '_' + name;
 | 
			
		||||
	Zotero.defineProperty(Zotero.Item.prototype, name, {
 | 
			
		||||
		get: function () { return this[prop]; },
 | 
			
		||||
		set: function (val) { return this.setField(name, val); }
 | 
			
		||||
	});
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
Zotero.defineProperty(Zotero.Item.prototype, 'itemTypeID', {
 | 
			
		||||
	get: function() { return this._itemTypeID; }
 | 
			
		||||
});
 | 
			
		||||
Zotero.defineProperty(Zotero.Item.prototype, 'dateAdded', {
 | 
			
		||||
	get: function() { return this._dateAdded; },
 | 
			
		||||
	set: function(val) { return this.setField('dateAdded', val); }
 | 
			
		||||
});
 | 
			
		||||
Zotero.defineProperty(Zotero.Item.prototype, 'dateModified', {
 | 
			
		||||
	get: function() { return this._dateModified; },
 | 
			
		||||
	set: function(val) { return this.setField('dateModified', val); }
 | 
			
		||||
});
 | 
			
		||||
Zotero.defineProperty(Zotero.Item.prototype, 'version', {
 | 
			
		||||
	get: function() { return this._version; },
 | 
			
		||||
	set: function(val) { return this.setField('version', val); }
 | 
			
		||||
});
 | 
			
		||||
Zotero.defineProperty(Zotero.Item.prototype, 'synced', {
 | 
			
		||||
	get: function() { return this._synced; },
 | 
			
		||||
	set: function(val) { return this.setField('synced', val); }
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
// .parentKey and .parentID defined in dataObject.js, but create aliases
 | 
			
		||||
Zotero.defineProperty(Zotero.Item.prototype, 'parentItemID', {
 | 
			
		||||
| 
						 | 
				
			
			@ -335,6 +323,8 @@ Zotero.Item.prototype._parseRowData = function(row) {
 | 
			
		|||
			case 'attachmentSyncState':
 | 
			
		||||
			case 'attachmentSyncedHash':
 | 
			
		||||
			case 'attachmentSyncedModificationTime':
 | 
			
		||||
			case 'createdByUserID':
 | 
			
		||||
			case 'lastModifiedByUserID':
 | 
			
		||||
				break;
 | 
			
		||||
			
 | 
			
		||||
			case 'itemID':
 | 
			
		||||
| 
						 | 
				
			
			@ -668,6 +658,19 @@ Zotero.Item.prototype.setField = function(field, value, loadIn) {
 | 
			
		|||
				value = !!value;
 | 
			
		||||
				break;
 | 
			
		||||
			
 | 
			
		||||
			case 'createdByUserID':
 | 
			
		||||
			case 'lastModifiedByUserID':
 | 
			
		||||
				if (typeof value != 'number' || value != parseInt(value)) {
 | 
			
		||||
					throw new Error(`${field} must be a number`);
 | 
			
		||||
				}
 | 
			
		||||
				if (!this._libraryID) {
 | 
			
		||||
					throw new Error(`libraryID must be set before setting ${field}`);
 | 
			
		||||
				}
 | 
			
		||||
				if (Zotero.Libraries.get(this._libraryID).libraryType != 'group') {
 | 
			
		||||
					throw new Error(`${field} is only valid for group library items`);
 | 
			
		||||
				}
 | 
			
		||||
				break;
 | 
			
		||||
			
 | 
			
		||||
			default:
 | 
			
		||||
				throw new Error('Primary field ' + field + ' cannot be changed in Zotero.Item.setField()');
 | 
			
		||||
			
 | 
			
		||||
| 
						 | 
				
			
			@ -1297,6 +1300,12 @@ Zotero.Item.prototype._saveData = Zotero.Promise.coroutine(function* (env) {
 | 
			
		|||
		}
 | 
			
		||||
	}
 | 
			
		||||
	
 | 
			
		||||
	if (this._changed.primaryData
 | 
			
		||||
			&& (this._changed.primaryData.createdByUserID || this._changed.primaryData.lastModifiedByUserID)) {
 | 
			
		||||
		let sql = "REPLACE INTO groupItems VALUES (?, ?, ?)";
 | 
			
		||||
		yield Zotero.DB.queryAsync(sql, [itemID, this._createdByUserID || null, this._lastModifiedByUserID || null]);
 | 
			
		||||
	}
 | 
			
		||||
	
 | 
			
		||||
	//
 | 
			
		||||
	// ItemData
 | 
			
		||||
	//
 | 
			
		||||
| 
						 | 
				
			
			@ -4783,13 +4792,6 @@ Zotero.Item.prototype.migrateExtraFields = function () {
 | 
			
		|||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
//////////////////////////////////////////////////////////////////////////////
 | 
			
		||||
//
 | 
			
		||||
// Asynchronous load methods
 | 
			
		||||
//
 | 
			
		||||
//////////////////////////////////////////////////////////////////////////////
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Return an item in the specified library equivalent to this item
 | 
			
		||||
 *
 | 
			
		||||
| 
						 | 
				
			
			@ -4816,6 +4818,34 @@ Zotero.Item.prototype.addLinkedItem = Zotero.Promise.coroutine(function* (item)
 | 
			
		|||
});
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Update createdByUserID/lastModifiedByUserID, efficiently
 | 
			
		||||
 *
 | 
			
		||||
 * Used by sync code
 | 
			
		||||
 */
 | 
			
		||||
Zotero.Item.prototype.updateCreatedByUser = async function (createdByUserID, lastModifiedByUserID) {
 | 
			
		||||
	this._createdByUserID = createdByUserID || null;
 | 
			
		||||
	this._lastModifiedByUserID = lastModifiedByUserID || null;
 | 
			
		||||
	
 | 
			
		||||
	var sql = "REPLACE INTO groupItems VALUES (?, ?, ?)";
 | 
			
		||||
	await Zotero.DB.queryAsync(sql, [this.id, this._createdByUserID, this._lastModifiedByUserID]);
 | 
			
		||||
	
 | 
			
		||||
	if (this._changed.primaryData) {
 | 
			
		||||
		for (let x of ['createdByUserID', 'lastModifiedByUserID']) {
 | 
			
		||||
			if (this._changed.primaryData[x]) {
 | 
			
		||||
				if (Objects.keys(this._changed.primaryData).length == 1) {
 | 
			
		||||
					delete this._changed.primaryData;
 | 
			
		||||
				}
 | 
			
		||||
				else {
 | 
			
		||||
					delete this._changed.primaryData[x];
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
//////////////////////////////////////////////////////////////////////////////
 | 
			
		||||
//
 | 
			
		||||
// Private methods
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -49,6 +49,9 @@ Zotero.Items = function() {
 | 
			
		|||
				version: "O.version",
 | 
			
		||||
				synced: "O.synced",
 | 
			
		||||
				
 | 
			
		||||
				createdByUserID: "createdByUserID",
 | 
			
		||||
				lastModifiedByUserID: "lastModifiedByUserID",
 | 
			
		||||
				
 | 
			
		||||
				firstCreator: _getFirstCreatorSQL(),
 | 
			
		||||
				sortCreator: _getSortCreatorSQL(),
 | 
			
		||||
				
 | 
			
		||||
| 
						 | 
				
			
			@ -79,7 +82,8 @@ Zotero.Items = function() {
 | 
			
		|||
		+ "LEFT JOIN items INoP ON (INo.parentItemID=INoP.itemID) "
 | 
			
		||||
		+ "LEFT JOIN deletedItems DI ON (O.itemID=DI.itemID) "
 | 
			
		||||
		+ "LEFT JOIN publicationsItems PI ON (O.itemID=PI.itemID) "
 | 
			
		||||
		+ "LEFT JOIN charsets CS ON (IA.charsetID=CS.charsetID)";
 | 
			
		||||
		+ "LEFT JOIN charsets CS ON (IA.charsetID=CS.charsetID)"
 | 
			
		||||
		+ "LEFT JOIN groupItems GI ON (O.itemID=GI.itemID)";
 | 
			
		||||
	
 | 
			
		||||
	this._relationsTable = "itemRelations";
 | 
			
		||||
	
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -3218,6 +3218,11 @@ Zotero.Schema = new function(){
 | 
			
		|||
				yield Zotero.DB.queryAsync("CREATE INDEX deletedSearches_dateDeleted ON deletedSearches(dateDeleted)");
 | 
			
		||||
			}
 | 
			
		||||
			
 | 
			
		||||
			else if (i == 112) {
 | 
			
		||||
				yield Zotero.DB.queryAsync("DROP TABLE IF EXISTS users");
 | 
			
		||||
				yield Zotero.DB.queryAsync("CREATE TABLE users (\n    userID INTEGER PRIMARY KEY,\n    name TEXT NOT NULL\n)");
 | 
			
		||||
			}
 | 
			
		||||
			
 | 
			
		||||
			// If breaking compatibility or doing anything dangerous, clear minorUpdateFrom
 | 
			
		||||
		}
 | 
			
		||||
		
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -223,6 +223,15 @@ Zotero.Sync.Data.Engine.prototype.start = Zotero.Promise.coroutine(function* ()
 | 
			
		|||
		skipNotifier: true
 | 
			
		||||
	});
 | 
			
		||||
	
 | 
			
		||||
	if (this.library.libraryType == 'group') {
 | 
			
		||||
		try {
 | 
			
		||||
			yield this._updateGroupItemUsers();
 | 
			
		||||
		}
 | 
			
		||||
		catch (e) {
 | 
			
		||||
			Zotero.logError(e);
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	
 | 
			
		||||
	Zotero.debug("Done syncing " + this.library.name);
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -1428,6 +1437,58 @@ Zotero.Sync.Data.Engine.prototype._uploadDeletions = Zotero.Promise.coroutine(fu
 | 
			
		|||
});
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Update createdByUserID/lastModifiedByUserID for previously downloaded group items
 | 
			
		||||
 *
 | 
			
		||||
 * TEMP: Currently only processes one batch of items, but before we start displaying the names,
 | 
			
		||||
 * we'll need to update it to fetch all
 | 
			
		||||
 */
 | 
			
		||||
Zotero.Sync.Data.Engine.prototype._updateGroupItemUsers = async function () {
 | 
			
		||||
	// TODO: Do more at once when we actually start showing these names
 | 
			
		||||
	var max = this.apiClient.MAX_OBJECTS_PER_REQUEST;
 | 
			
		||||
	
 | 
			
		||||
	var sql = "SELECT key FROM items LEFT JOIN groupItems GI USING (itemID) "
 | 
			
		||||
		+ `WHERE libraryID=? AND GI.itemID IS NULL ORDER BY itemID LIMIT ${max}`;
 | 
			
		||||
	var keys = await Zotero.DB.columnQueryAsync(sql, this.libraryID);
 | 
			
		||||
	if (!keys.length) {
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	
 | 
			
		||||
	Zotero.debug(`Updating item users in ${this.library.name}`);
 | 
			
		||||
	
 | 
			
		||||
	var jsonItems = await this.apiClient.downloadObjects(
 | 
			
		||||
		this.library.libraryType, this.libraryTypeID, 'item', keys
 | 
			
		||||
	)[0];
 | 
			
		||||
	
 | 
			
		||||
	if (!Array.isArray(jsonItems)) {
 | 
			
		||||
		Zotero.logError(e);
 | 
			
		||||
		return;
 | 
			
		||||
	}
 | 
			
		||||
	
 | 
			
		||||
	for (let jsonItem of jsonItems) {
 | 
			
		||||
		let item = Zotero.Items.getByLibraryAndKey(this.libraryID, jsonItem.key);
 | 
			
		||||
		let params = [null, null];
 | 
			
		||||
		
 | 
			
		||||
		// This should almost always exist, but maybe doesn't for some old items?
 | 
			
		||||
		if (jsonItem.meta.createdByUser) {
 | 
			
		||||
			let { id: userID, username, name } = jsonItem.meta.createdByUser;
 | 
			
		||||
			await Zotero.Users.setName(userID, name !== '' ? name : username);
 | 
			
		||||
			params[0] = userID;
 | 
			
		||||
		}
 | 
			
		||||
		
 | 
			
		||||
		if (jsonItem.meta.lastModifiedByUser) {
 | 
			
		||||
			let { id: userID, username, name } = jsonItem.meta.lastModifiedByUser;
 | 
			
		||||
			await Zotero.Users.setName(userID, name !== '' ? name : username);
 | 
			
		||||
			params[1] = userID;
 | 
			
		||||
		}
 | 
			
		||||
		
 | 
			
		||||
		await item.updateCreatedByUser.apply(item, params);
 | 
			
		||||
	}
 | 
			
		||||
	
 | 
			
		||||
	return;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
Zotero.Sync.Data.Engine.prototype._getJSONForObject = function (objectType, id, options = {}) {
 | 
			
		||||
	return Zotero.DB.executeTransaction(function* () {
 | 
			
		||||
		var objectsClass = Zotero.DataObjectUtilities.getObjectsClassForObjectType(objectType);
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1459,8 +1459,23 @@ Zotero.Sync.Data.Local = {
 | 
			
		|||
			if (!options.skipData) {
 | 
			
		||||
				obj.fromJSON(json.data, { strict: true });
 | 
			
		||||
			}
 | 
			
		||||
			if (obj.objectType == 'item' && obj.isImportedAttachment()) {
 | 
			
		||||
				yield this._checkAttachmentForDownload(obj, json.data.mtime, options.isNewObject);
 | 
			
		||||
			if (obj.objectType == 'item') {
 | 
			
		||||
				// Update createdByUserID and lastModifiedByUserID
 | 
			
		||||
				for (let p of ['createdByUser', 'lastModifiedByUser']) {
 | 
			
		||||
					if (json.meta && json.meta[p]) {
 | 
			
		||||
						let { id: userID, username, name } = json.meta[p];
 | 
			
		||||
						obj[p + 'ID'] = userID;
 | 
			
		||||
						name = name !== '' ? name : username;
 | 
			
		||||
						// Update stored name if it changed
 | 
			
		||||
						if (Zotero.Users.getName(userID) != name) {
 | 
			
		||||
							yield Zotero.Users.setName(userID, name);
 | 
			
		||||
						}
 | 
			
		||||
					}
 | 
			
		||||
				}
 | 
			
		||||
				
 | 
			
		||||
				if (obj.isImportedAttachment()) {
 | 
			
		||||
					yield this._checkAttachmentForDownload(obj, json.data.mtime, options.isNewObject);
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
			obj.version = json.data.version;
 | 
			
		||||
			if (!options.saveAsUnsynced) {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -28,10 +28,11 @@ Zotero.Users = new function () {
 | 
			
		|||
	var _libraryID;
 | 
			
		||||
	var _username;
 | 
			
		||||
	var _localUserKey;
 | 
			
		||||
	var _users = {};
 | 
			
		||||
	
 | 
			
		||||
	this.init = Zotero.Promise.coroutine(function* () {
 | 
			
		||||
	this.init = async function () {
 | 
			
		||||
		let sql = "SELECT key, value FROM settings WHERE setting='account'";
 | 
			
		||||
		let rows = yield Zotero.DB.queryAsync(sql);
 | 
			
		||||
		let rows = await Zotero.DB.queryAsync(sql);
 | 
			
		||||
		
 | 
			
		||||
		let settings = {};
 | 
			
		||||
		for (let i=0; i<rows.length; i++) {
 | 
			
		||||
| 
						 | 
				
			
			@ -56,11 +57,16 @@ Zotero.Users = new function () {
 | 
			
		|||
			let key = Zotero.randomString(8);
 | 
			
		||||
			
 | 
			
		||||
			sql = "INSERT INTO settings VALUES ('account', 'localUserKey', ?)";
 | 
			
		||||
			yield Zotero.DB.queryAsync(sql, key);
 | 
			
		||||
			await Zotero.DB.queryAsync(sql, key);
 | 
			
		||||
			
 | 
			
		||||
			_localUserKey = key;
 | 
			
		||||
		}
 | 
			
		||||
	});
 | 
			
		||||
		
 | 
			
		||||
		rows = await Zotero.DB.queryAsync("SELECT userID, name FROM users");
 | 
			
		||||
		for (let row of rows) {
 | 
			
		||||
			_users[row.userID] = row.name;
 | 
			
		||||
		}
 | 
			
		||||
	};
 | 
			
		||||
	
 | 
			
		||||
	
 | 
			
		||||
	this.getCurrentUserID = function() { return _userID };
 | 
			
		||||
| 
						 | 
				
			
			@ -87,4 +93,18 @@ Zotero.Users = new function () {
 | 
			
		|||
	this.getLocalUserKey = function () {
 | 
			
		||||
		return _localUserKey;
 | 
			
		||||
	};
 | 
			
		||||
	
 | 
			
		||||
	
 | 
			
		||||
	this.getName = function (userID) {
 | 
			
		||||
		return _users[userID] || '';
 | 
			
		||||
	};
 | 
			
		||||
	
 | 
			
		||||
	
 | 
			
		||||
	this.setName = async function (userID, name) {
 | 
			
		||||
		if (this.getName(userID) == name) {
 | 
			
		||||
			return;
 | 
			
		||||
		}
 | 
			
		||||
		await Zotero.DB.queryAsync("REPLACE INTO users VALUES (?, ?)", [userID, name]);
 | 
			
		||||
		_users[userID] = name;
 | 
			
		||||
	}
 | 
			
		||||
};
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,4 +1,4 @@
 | 
			
		|||
-- 111
 | 
			
		||||
-- 112
 | 
			
		||||
 | 
			
		||||
-- Copyright (c) 2009 Center for History and New Media
 | 
			
		||||
--                    George Mason University, Fairfax, Virginia, USA
 | 
			
		||||
| 
						 | 
				
			
			@ -275,7 +275,7 @@ CREATE TABLE libraries (
 | 
			
		|||
 | 
			
		||||
CREATE TABLE users (
 | 
			
		||||
    userID INTEGER PRIMARY KEY,
 | 
			
		||||
    username TEXT NOT NULL
 | 
			
		||||
    name TEXT NOT NULL
 | 
			
		||||
);
 | 
			
		||||
 | 
			
		||||
CREATE TABLE groups (
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -4046,6 +4046,85 @@ describe("Zotero.Sync.Data.Engine", function () {
 | 
			
		|||
	});
 | 
			
		||||
	
 | 
			
		||||
	
 | 
			
		||||
	describe("#_updateGroupItemUsers()", function () {
 | 
			
		||||
		it("should update createdByUserID and lastModifiedByUserID", async function () {
 | 
			
		||||
			var { id: groupID, libraryID } = await createGroup();
 | 
			
		||||
			({ engine, client, caller } = await setup({ libraryID }));
 | 
			
		||||
			
 | 
			
		||||
			var item1 = await createDataObject('item', { libraryID });
 | 
			
		||||
			var item1DateModified = item1.dateModified;
 | 
			
		||||
			var item2 = await createDataObject('item', { libraryID });
 | 
			
		||||
			var responseJSON = [
 | 
			
		||||
				item1.toResponseJSON(),
 | 
			
		||||
				item2.toResponseJSON()
 | 
			
		||||
			];
 | 
			
		||||
			responseJSON[0].meta.createdByUser = {
 | 
			
		||||
				id: 152315,
 | 
			
		||||
				username: "user152315",
 | 
			
		||||
				name: "User 152315"
 | 
			
		||||
			};
 | 
			
		||||
			responseJSON[0].meta.lastModifiedByUser = {
 | 
			
		||||
				id: 352352,
 | 
			
		||||
				username: "user352352",
 | 
			
		||||
				name: "User 352352"
 | 
			
		||||
			};
 | 
			
		||||
			responseJSON[1].meta.createdByUser = {
 | 
			
		||||
				id: 346534,
 | 
			
		||||
				username: "user346534",
 | 
			
		||||
				name: "User 346534"
 | 
			
		||||
			};
 | 
			
		||||
			
 | 
			
		||||
			setResponse({
 | 
			
		||||
				method: "GET",
 | 
			
		||||
				url: `groups/${groupID}/items?itemKey=${item1.key}%2C${item2.key}&includeTrashed=1`,
 | 
			
		||||
				status: 200,
 | 
			
		||||
				headers: {
 | 
			
		||||
					"Last-Modified-Version": 5
 | 
			
		||||
				},
 | 
			
		||||
				json: responseJSON
 | 
			
		||||
			});
 | 
			
		||||
			
 | 
			
		||||
			await engine._updateGroupItemUsers();
 | 
			
		||||
			
 | 
			
		||||
			assert.equal(item1.createdByUserID, 152315);
 | 
			
		||||
			assert.equal(item1.lastModifiedByUserID, 352352);
 | 
			
		||||
			assert.equal(item1.dateModified, item1DateModified);
 | 
			
		||||
			assert.equal(item2.createdByUserID, 346534);
 | 
			
		||||
		});
 | 
			
		||||
		
 | 
			
		||||
		
 | 
			
		||||
		it("should use username if no name", async function () {
 | 
			
		||||
			var { id: groupID, libraryID } = await createGroup();
 | 
			
		||||
			({ engine, client, caller } = await setup({ libraryID }));
 | 
			
		||||
			
 | 
			
		||||
			var item = await createDataObject('item', { libraryID });
 | 
			
		||||
			var responseJSON = [
 | 
			
		||||
				item.toResponseJSON()
 | 
			
		||||
			];
 | 
			
		||||
			responseJSON[0].meta.createdByUser = {
 | 
			
		||||
				id: 235235,
 | 
			
		||||
				username: "user235235",
 | 
			
		||||
				name: ""
 | 
			
		||||
			};
 | 
			
		||||
			
 | 
			
		||||
			setResponse({
 | 
			
		||||
				method: "GET",
 | 
			
		||||
				url: `groups/${groupID}/items?itemKey=${item.key}&includeTrashed=1`,
 | 
			
		||||
				status: 200,
 | 
			
		||||
				headers: {
 | 
			
		||||
					"Last-Modified-Version": 6
 | 
			
		||||
				},
 | 
			
		||||
				json: responseJSON
 | 
			
		||||
			});
 | 
			
		||||
			
 | 
			
		||||
			await engine._updateGroupItemUsers();
 | 
			
		||||
			
 | 
			
		||||
			assert.equal(item.createdByUserID, 235235);
 | 
			
		||||
			assert.equal(Zotero.Users.getName(235235), 'user235235');
 | 
			
		||||
		});
 | 
			
		||||
	});
 | 
			
		||||
	
 | 
			
		||||
	
 | 
			
		||||
	describe("#_upgradeCheck()", function () {
 | 
			
		||||
		it("should upgrade a library last synced with the classic sync architecture", function* () {
 | 
			
		||||
			var userLibraryID = Zotero.Libraries.userLibraryID;
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -930,6 +930,69 @@ describe("Zotero.Sync.Data.Local", function() {
 | 
			
		|||
				"SELECT COUNT(*) FROM items WHERE libraryID=? AND key=?", [libraryID, key2]
 | 
			
		||||
			), 0);
 | 
			
		||||
		});
 | 
			
		||||
		
 | 
			
		||||
		it("should update createdByUser and lastModifiedBy when saving group item", async function () {
 | 
			
		||||
			var { libraryID } = await getGroup();
 | 
			
		||||
			let item = await createDataObject('item', { libraryID });
 | 
			
		||||
			let data = item.toJSON();
 | 
			
		||||
			data.key = item.key;
 | 
			
		||||
			data.version = 10;
 | 
			
		||||
			let json = {
 | 
			
		||||
				key: item.key,
 | 
			
		||||
				version: 10,
 | 
			
		||||
				meta: {
 | 
			
		||||
					createdByUser: {
 | 
			
		||||
						id: 12345,
 | 
			
		||||
						username: 'foo',
 | 
			
		||||
						name: 'Foo Foo'
 | 
			
		||||
					},
 | 
			
		||||
					lastModifiedByUser: {
 | 
			
		||||
						id: 23456,
 | 
			
		||||
						username: 'bar',
 | 
			
		||||
						name: 'Bar Bar'
 | 
			
		||||
					}
 | 
			
		||||
				},
 | 
			
		||||
				data
 | 
			
		||||
			};
 | 
			
		||||
			await Zotero.Sync.Data.Local.processObjectsFromJSON(
 | 
			
		||||
				'item', libraryID, [json], { stopOnError: true }
 | 
			
		||||
			);
 | 
			
		||||
			let localItem = Zotero.Items.getByLibraryAndKey(libraryID, item.key);
 | 
			
		||||
			assert.isTrue(localItem.synced);
 | 
			
		||||
			
 | 
			
		||||
			assert.equal(localItem.createdByUserID, 12345);
 | 
			
		||||
			assert.equal(localItem.lastModifiedByUserID, 23456);
 | 
			
		||||
			assert.equal(Zotero.Users.getName(12345), 'Foo Foo');
 | 
			
		||||
			assert.equal(Zotero.Users.getName(23456), 'Bar Bar');
 | 
			
		||||
		});
 | 
			
		||||
		
 | 
			
		||||
		it("should use username if empty name for createdByUser when saving group item", async function () {
 | 
			
		||||
			var { libraryID } = await getGroup();
 | 
			
		||||
			let item = await createDataObject('item', { libraryID });
 | 
			
		||||
			let data = item.toJSON();
 | 
			
		||||
			data.key = item.key;
 | 
			
		||||
			data.version = 10;
 | 
			
		||||
			let json = {
 | 
			
		||||
				key: item.key,
 | 
			
		||||
				version: 10,
 | 
			
		||||
				meta: {
 | 
			
		||||
					createdByUser: {
 | 
			
		||||
						id: 12345,
 | 
			
		||||
						username: 'foo',
 | 
			
		||||
						name: ''
 | 
			
		||||
					},
 | 
			
		||||
				},
 | 
			
		||||
				data
 | 
			
		||||
			};
 | 
			
		||||
			await Zotero.Sync.Data.Local.processObjectsFromJSON(
 | 
			
		||||
				'item', libraryID, [json], { stopOnError: true }
 | 
			
		||||
			);
 | 
			
		||||
			let localItem = Zotero.Items.getByLibraryAndKey(libraryID, item.key);
 | 
			
		||||
			assert.isTrue(localItem.synced);
 | 
			
		||||
			
 | 
			
		||||
			assert.equal(localItem.createdByUserID, 12345);
 | 
			
		||||
			assert.equal(Zotero.Users.getName(12345), 'foo');
 | 
			
		||||
		});
 | 
			
		||||
	})
 | 
			
		||||
	
 | 
			
		||||
	describe("Sync Queue", function () {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue