diff --git a/chrome/content/zotero/xpcom/cite.js b/chrome/content/zotero/xpcom/cite.js index b298f9547..6c4f44ffb 100644 --- a/chrome/content/zotero/xpcom/cite.js +++ b/chrome/content/zotero/xpcom/cite.js @@ -638,7 +638,7 @@ Zotero.CSL.prototype.formatBibliography = function(itemSet, format) { } else { if(format == "RTF" || format == "Integration") { if(format == "RTF") { - preamble = "{\\rtf\\ansi{\\fonttbl\\f0\\froman Times New Roman;}{\\colortbl;\\red255\\green255\\blue255;}\\pard\\f0"; + preamble = "{\\rtf\\ansi{\\fonttbl\\f0\\froman Times New Roman;}{\\colortbl;\\red255\\green255\\blue255;}\\pard\\f0\r\n"; } var tabStop = null; @@ -774,7 +774,7 @@ Zotero.CSL.prototype.formatBibliography = function(itemSet, format) { output = output.substr(0, output.length-returnChars.length); // add bracket for RTF - if(format == "RTF") output += "}"; + if(format == "RTF") output += "\\par }"; } return preamble+output; diff --git a/chrome/content/zotero/xpcom/integration.js b/chrome/content/zotero/xpcom/integration.js index 7bcc50682..bec2d57ea 100644 --- a/chrome/content/zotero/xpcom/integration.js +++ b/chrome/content/zotero/xpcom/integration.js @@ -15,19 +15,23 @@ distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and - limitations under the License. + limitations under the License.s ***** END LICENSE BLOCK ***** */ -const API_VERSION = 5; +const API_VERSION = 1; +const COMPAT_API_VERSION = 5; Zotero.Integration = new function() { var _contentLengthRe = /[\r\n]Content-Length: *([0-9]+)/i; var _XMLRe = /<\?[^>]+\?>/; var _onlineObserverRegistered; - this.ns = "http://www.zotero.org/namespaces/SOAP"; + this.sessions = {}; + + var ns = "http://www.zotero.org/namespaces/SOAP"; + this.ns = ns; this.init = init; this.handleHeader = handleHeader; @@ -37,6 +41,8 @@ Zotero.Integration = new function() { * initializes a very rudimentary web server used for SOAP RPC */ function init() { + this.env = new Namespace("http://schemas.xmlsoap.org/soap/envelope/"); + if (Zotero.Utilities.HTTP.browserIsOffline()) { Zotero.debug('Browser is offline -- not initializing integration HTTP server'); _registerOnlineObserver() @@ -89,15 +95,16 @@ Zotero.Integration = new function() { function handleEnvelope(envelope) { Zotero.debug("Integration: SOAP Request\n"+envelope); envelope = envelope.replace(_XMLRe, ""); + var env = this.env; - var env = new Namespace("http://schemas.xmlsoap.org/soap/envelope/"); var xml = new XML(envelope); var request = xml.env::Body.children()[0]; if(request.namespace() != this.ns) { Zotero.debug("Integration: SOAP method not supported: invalid namespace"); - } else { + } else if(!xml.env::Header.children().length()) { + // old style SOAP request var name = request.localName(); - if(Zotero.Integration.SOAP[name]) { + if(Zotero.Integration.SOAP_Compat[name]) { if(request.input.length()) { // split apart passed parameters (same colon-escaped format // as we pass) @@ -126,7 +133,7 @@ Zotero.Integration = new function() { } // execute request - var output = Zotero.Integration.SOAP[name](vars); + var output = Zotero.Integration.SOAP_Compat[name](vars); // ugh: we can't use real SOAP, since AppleScript VBA can't pass // objects, so implode arrays @@ -161,6 +168,11 @@ Zotero.Integration = new function() { } else { Zotero.debug("Integration: SOAP method not supported"); } + } else { + // execute request + request = new Zotero.Integration.Request(xml); + return _generateResponse(request.status+" "+request.statusText, + 'text/xml; charset="UTF-8"', request.responseText); } } @@ -381,30 +393,223 @@ Zotero.Integration.DataListener.prototype._requestFinished = function(response) } } -Zotero.Integration.SOAP = new function() { +Zotero.Integration.Request = function(xml) { + default xml namespace = Zotero.Integration.ns; with({}); + + var env = Zotero.Integration.env; + this.header = xml.env::Header; + this.body = xml.env::Body; + + this.responseXML = + + + + + this.responseHeader = this.responseXML.env::Header; + this.responseBody = this.responseXML.env::Body; + + this.needPrefs = this.body.setDocPrefs.length(); + + try { + this.initializeSession(); + if(this.needPrefs) { + this.setDocPrefs(); + } + if(this.body.updateCitations.length() || this.body.updateBibliography.length()) { + this.processCitations(); + } + + this.status = 200; + this.statusText = "OK"; + } catch(e) { + Components.utils.reportError(e); + + Zotero.debug(e); + + // Get a code for this error + var code = (e.name ? e.name : "GenericError"); + var text = e.toString(); + try { + var text = Zotero.getString("integration.error."+e, Zotero.version); + code = e; + } catch(e) { + } + + this.responseXML = + + + + XML-ENV:Sender + z:{code} + + + + {text} + + + + + this.status = 500; + this.statusText = "Internal Server Error"; + } + + // Zap chars that we don't want in our output + this.responseText = this.responseXML.toXMLString().replace(/[\x00-\x08\x0B\x0C\x0E-\x1F]/g, ''); + Zotero.debug("Integration: SOAP Response\n"+this.responseText); +} + +/** + * Gets session data to associate with a request + **/ +Zotero.Integration.Request.prototype.initializeSession = function() { + default xml namespace = Zotero.Integration.ns; with({}); + + if(this.header.client.@api != API_VERSION) { + throw "incompatibleVersion"; + } + + var styleID = this.header.style.@id.toString(); + this._sessionID = this.header.session.@id.toString(); + if(this._sessionID === "" || !Zotero.Integration.sessions[this._sessionID]) { + this._sessionID = Zotero.randomString(); + this._session = Zotero.Integration.sessions[this._sessionID] = new Zotero.Integration.Session(); + + var preferences = {}; + for each(var pref in this.header.prefs.pref) { + preferences[pref.@name] = pref.@value.toString(); + } + + this.needPrefs = this.needPrefs || !this._session.setStyle(styleID, preferences); + if(this.header.bibliography.length()) { + session.loadBibliographyData(Zotero.Utilities.prototype.trim(this.header.bibliography.toString())); + } + } else { + this._session = Zotero.Integration.sessions[this._sessionID]; + } + + this.responseHeader.appendChild(); +} + +/** + * Sets preferences + **/ +Zotero.Integration.Request.prototype.setDocPrefs = function() { + default xml namespace = Zotero.Integration.ns; with({}); + + var io = new function() { + this.wrappedJSObject = this; + } + + io.openOffice = this.header.client.@agent == "OpenOffice.org" + + var oldStyle = io.style = this._session.styleID; + io.useEndnotes = this._session.prefs.useEndnotes; + io.useBookmarks = this._session.prefs.fieldType; + + this.watcher = Components.classes["@mozilla.org/embedcomp/window-watcher;1"] + .getService(Components.interfaces.nsIWindowWatcher) + .openWindow(null, 'chrome://zotero/content/integrationDocPrefs.xul', '', + 'chrome,modal,centerscreen' + (Zotero.isWin ? ',popup' : ''), io, true); + this._session.prefs.useEndnotes = io.useEndnotes; + this._session.prefs.fieldType = io.useBookmarks; + Zotero.debug("prefs are") + Zotero.debug(this._session.prefs); + if(!oldStyle || oldStyle != io.style + || io.useEndnotes != this._session.prefs.useEndnotes + || io.useBookmarks != this._session.prefs.fieldType) { + this._session.regenerateAll = this._session.bibliographyHasChanged = true; + this._session.setStyle(io.style, this._session.prefs); + } + + this.responseHeader.appendChild(