From a8bb8dae4013193d449495a6cf04de496ae476a9 Mon Sep 17 00:00:00 2001 From: Dan Stillman Date: Sun, 31 Aug 2008 23:36:01 +0000 Subject: [PATCH] Adds WebDAV file sync - Still experimental and incomplete, with no lock support and not much error handling Also: - New expiry date for sync functions - Attachment character set was being dropped during syncing - Possibly improves sizing issues with preferences window - Fixes problems with attachment filenames with extended characters - Fixes some problem with tags that I don't remember - Makes XMLHTTPRequest calls are now background requests (no auth windows or other prompts) - Z.U.HTTP.doOptions() now takes an nsIURI instead of a URL spec - New methods: - Zotero.Utilities.rand(min, max) - Zotero.Utilities.probability(x) - Zotero.Utilities.Base64.encode(str) and decode(str) - Zotero.getTempDirectory() - Zotero.Date.dateToISO(date) - convert JS Date object to ISO 8601 UTC date/time - Zotero.Date.isoToDate(isoDate) - convert an ISO 8601 UTC date/time to a JS Date object --- chrome/content/zotero/overlay.xul | 43 +- .../content/zotero/preferences/preferences.js | 164 ++ .../zotero/preferences/preferences.xul | 136 +- chrome/content/zotero/xpcom/attachments.js | 51 +- chrome/content/zotero/xpcom/data/item.js | 181 +- chrome/content/zotero/xpcom/data/items.js | 5 + chrome/content/zotero/xpcom/schema.js | 8 + chrome/content/zotero/xpcom/storage.js | 2168 +++++++++++++++++ chrome/content/zotero/xpcom/sync.js | 384 ++- chrome/content/zotero/xpcom/utilities.js | 430 +++- chrome/content/zotero/xpcom/zotero.js | 85 +- chrome/locale/en-US/zotero/zotero.dtd | 6 +- chrome/locale/en-US/zotero/zotero.properties | 5 +- chrome/skin/default/zotero/drive_network.png | Bin 0 -> 585 bytes chrome/skin/default/zotero/overlay.css | 21 +- chrome/skin/default/zotero/preferences.css | 52 +- components/zotero-service.js | 1 + defaults/preferences/zotero.js | 11 +- userdata.sql | 11 +- 19 files changed, 3516 insertions(+), 246 deletions(-) create mode 100644 chrome/content/zotero/xpcom/storage.js create mode 100755 chrome/skin/default/zotero/drive_network.png diff --git a/chrome/content/zotero/overlay.xul b/chrome/content/zotero/overlay.xul index a9c3e95ab9..f4d487f129 100644 --- a/chrome/content/zotero/overlay.xul +++ b/chrome/content/zotero/overlay.xul @@ -133,6 +133,10 @@ + + + + @@ -305,16 +309,49 @@ - + + + + + + + + + + + + + + + + + + + oncommand="Zotero.Sync.Runner.sync()"> + noautohide="true"> + diff --git a/chrome/content/zotero/preferences/preferences.js b/chrome/content/zotero/preferences/preferences.js index a2003390b8..b68bd5efcb 100644 --- a/chrome/content/zotero/preferences/preferences.js +++ b/chrome/content/zotero/preferences/preferences.js @@ -137,6 +137,170 @@ function populateOpenURLResolvers() { } +// +// Sync +// +function unverifyStorageServer() { + Zotero.debug("Clearing storage settings"); + Zotero.Sync.Storage.clearSettingsCache(); + Zotero.Prefs.set('sync.storage.verified', false); +} + +function verifyStorageServer() { + Zotero.debug("Verifying storage"); + + var verifyButton = document.getElementById("storage-verify"); + var abortButton = document.getElementById("storage-abort"); + var progressMeter = document.getElementById("storage-progress"); + + var callback = function (uri, status, authRequired) { + verifyButton.hidden = false; + abortButton.hidden = true; + progressMeter.hidden = true; + + var promptService = + Components.classes["@mozilla.org/network/default-prompt;1"]. + createInstance(Components.interfaces.nsIPrompt); + if (uri) { + var spec = uri.scheme + '://' + uri.hostPort + uri.path; + } + + switch (status) { + case Zotero.Sync.Storage.SUCCESS: + promptService.alert( + "Server configuration verified", + "File storage is successfully set up." + ); + Zotero.Prefs.set("sync.storage.verified", true); + return true; + + case Zotero.Sync.Storage.ERROR_NO_URL: + var errorMessage = "Please enter a URL."; + setTimeout(function () { + document.getElementById("storage-url").focus(); + }, 1); + break; + + case Zotero.Sync.Storage.ERROR_NO_USERNAME: + var errorMessage = "Please enter a username."; + setTimeout(function () { + document.getElementById("storage-username").focus(); + }, 1); + break; + + case Zotero.Sync.Storage.ERROR_NO_PASSWORD: + var errorMessage = "Please enter a password."; + setTimeout(function () { + document.getElementById("storage-password").focus(); + }, 1); + break; + + case Zotero.Sync.Storage.ERROR_UNREACHABLE: + var errorMessage = "The server " + uri.host + " could not be reached."; + break; + + case Zotero.Sync.Storage.ERROR_NOT_DAV: + var errorMessage = spec + " is not a valid WebDAV URL."; + break; + + case Zotero.Sync.Storage.ERROR_AUTH_FAILED: + var errorTitle = "Permission denied"; + var errorMessage = "The server did not accept the username and " + + "password you entered." + " " + + "Please check your server settings " + + "or contact your server administrator."; + break; + + case Zotero.Sync.Storage.ERROR_FORBIDDEN: + var errorTitle = "Permission denied"; + var errorMessage = "You don't have permission to access " + + uri.path + " on this server." + " " + + "Please check your server settings " + + "or contact your server administrator."; + break; + + case Zotero.Sync.Storage.ERROR_PARENT_DIR_NOT_FOUND: + var errorTitle = "Directory not found"; + var parentSpec = spec.replace(/\/zotero\/$/, ""); + var errorMessage = parentSpec + " does not exist."; + break; + + case Zotero.Sync.Storage.ERROR_ZOTERO_DIR_NOT_FOUND: + var create = promptService.confirmEx( + // TODO: localize + "Directory not found", + spec + " does not exist.\n\nDo you want to create it now?", + promptService.BUTTON_POS_0 + * promptService.BUTTON_TITLE_IS_STRING + + promptService.BUTTON_POS_1 + * promptService.BUTTON_TITLE_CANCEL, + "Create", + null, null, null, {} + ); + + if (create != 0) { + return; + } + + Zotero.Sync.Storage.createServerDirectory(function (uri, status) { + switch (status) { + case Zotero.Sync.Storage.SUCCESS: + promptService.alert( + "Server configuration verified", + "File storage is successfully set up." + ); + Zotero.Prefs.set("sync.storage.verified", true); + return true; + + case Zotero.Sync.Storage.ERROR_FORBIDDEN: + var errorTitle = "Permission denied"; + var errorMessage = "You do not have " + + "permission to create a Zotero directory " + + "at the following address:" + "\n\n" + spec; + errorMessage += "\n\n" + + "Please check your server settings or " + + "contact your server administrator."; + break; + } + + // TEMP + if (!errorMessage) { + var errorMessage = status; + } + promptService.alert(errorTitle, errorMessage); + }); + + return false; + } + + if (!errorTitle) { + var errorTitle = Zotero.getString("general.error"); + } + // TEMP + if (!errorMessage) { + var errorMessage = status; + } + promptService.alert(errorTitle, errorMessage); + return false; + } + + verifyButton.hidden = true; + abortButton.hidden = false; + progressMeter.hidden = false; + var requestHolder = Zotero.Sync.Storage.checkServer(callback); + abortButton.onclick = function () { + if (requestHolder.request) { + requestHolder.request.onreadystatechange = undefined; + requestHolder.request.abort(); + verifyButton.hidden = false; + abortButton.hidden = true; + progressMeter.hidden = true; + } + } +} + + + /* * Builds the main Quick Copy drop-down from the current global pref */ diff --git a/chrome/content/zotero/preferences/preferences.xul b/chrome/content/zotero/preferences/preferences.xul index 7180b20ed8..3e8100e0c8 100644 --- a/chrome/content/zotero/preferences/preferences.xul +++ b/chrome/content/zotero/preferences/preferences.xul @@ -156,31 +156,116 @@ To add a new preference: - + + + + + - - - - - + + - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +