diff options
author | niko <niko> | 2012-10-06 23:25:33 (GMT) |
---|---|---|
committer | niko <niko> | 2012-10-06 23:25:33 (GMT) |
commit | 1b345176e3942b5909862878e772bfe83b6c9f94 (patch) | |
tree | 93b84269eff1e5d244887d193415ba80f2ab72bd /src | |
parent | 32c1661206a070f04a15fc024464f91e932aac35 (diff) | |
download | synckolab-1b345176e3942b5909862878e772bfe83b6c9f94.tar.gz |
reading of kolab3 format - unit tests
Diffstat (limited to 'src')
-rw-r--r-- | src/chrome/content/synckolab/addressbookTools.js | 288 | ||||
-rw-r--r-- | src/chrome/content/synckolab/config.js | 8 | ||||
-rw-r--r-- | src/chrome/content/synckolab/tools.js | 82 | ||||
-rw-r--r-- | src/chrome/content/synckolab/tools/text.js | 245 | ||||
-rw-r--r-- | src/chrome/content/synckolab/wndConfig.js | 36 |
5 files changed, 541 insertions, 118 deletions
diff --git a/src/chrome/content/synckolab/addressbookTools.js b/src/chrome/content/synckolab/addressbookTools.js index db4a96c..a88e322 100644 --- a/src/chrome/content/synckolab/addressbookTools.js +++ b/src/chrome/content/synckolab/addressbookTools.js @@ -592,9 +592,17 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { synckolab.tools.logMessage("Error parsing the XML content of this message.\n" + xml, synckolab.global.LOG_ERROR + synckolab.global.LOG_AB); return null; } - if ((topNode.nodeType !== Node.ELEMENT_NODE) || (topNode.nodeName.toUpperCase() !== "CONTACT")) { - - if ((topNode.nodeType === Node.ELEMENT_NODE) && (topNode.nodeName.toUpperCase() === "DISTRIBUTION-LIST")) { + + // format detection + + if ((topNode.nodeType !== Node.ELEMENT_NODE) || + ((topNode.nodeName.toUpperCase() !== "CONTACT") && // kolab2 + (topNode.nodeName.toUpperCase() !== "VCARDS") // kolab 3 + )) { + + if ((topNode.nodeType === Node.ELEMENT_NODE) && + (topNode.nodeName.toUpperCase() === "DISTRIBUTION-LIST")) { + // TODO kolab 3 return this.Xml2List(topNode, card); } // this can't be an event in Kolab XML format @@ -602,7 +610,19 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { return null; } - cur = new synckolab.Node(topNode.firstChild); + if(topNode.nodeName.toUpperCase() === "VCARDS") { + // kolab 3: vcard container: vcards / vcard / uid + synckolab.tools.logMessage("Kolab 3 XML VCARDS", synckolab.global.LOG_DEBUG + synckolab.global.LOG_AB); + cur = new synckolab.Node(topNode); + cur = cur.getChildNode("VCARD"); + cur = new synckolab.Node(cur.firstChild); + } + else + { + // kolab 2: start parsing directly: contact / product-id + synckolab.tools.logMessage("Kolab 2 XML CONTACT", synckolab.global.LOG_DEBUG + synckolab.global.LOG_AB); + cur = new synckolab.Node(topNode.firstChild); + } } else { synckolab.tools.logMessage("parsing dom tree into card.", synckolab.global.LOG_DEBUG + synckolab.global.LOG_AB); cur = new synckolab.Node(xml.firstChild); @@ -611,11 +631,36 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { var found = false; var tok; // for tokenizer var email = 0; + var num; // temp while (cur) { if (cur.nodeType === Node.ELEMENT_NODE)//1 { switch (cur.nodeName.toUpperCase()) { + // KOLAB 2+3 + case "UID": + if (cur.firstChild === null) { + break; + } + // kolab 3: uid/uri + var uid = cur.getXmlResult("URI", ""); + // kolab2: directly + if(uid === "") { + uid = cur.getFirstData(); + } + this.setUID(card, uid); + break; + // timestamp + case "REV": + /* + ignore this since thunderbird implementation just does not work + var s = cur.getXmlResult("TIMESTAMP", ""); + // now we gotta check times... convert the message first + // save the date in microseconds + // 20050330T152852Z + + */ + break; case "LAST-MODIFICATION-DATE": /* ignore this since thunderbird implementation just does not work @@ -635,7 +680,8 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { } */ break; - + + // KOLAB 2 case "NAME": this.setCardProperty(card, "FirstName", cur.getXmlResult("GIVEN-NAME", "")); this.setCardProperty(card, "LastName", cur.getXmlResult("LAST-NAME", "")); @@ -643,7 +689,16 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { found = true; break; - case "DISPLAY-NAME": + // KOLAB 3 + case "N": + this.setCardProperty(card, "FirstName", cur.getXmlResult("SURNAME", "")); + this.setCardProperty(card, "LastName", cur.getXmlResult("GIVEN", "")); + // others: ADDITIONAL/PREFIX/SUFFIX + found = true; + break; + + case "FN": // kolab 3 + case "DISPLAY-NAME": // kolab 2 this.setCardProperty(card, "DisplayName", cur.getFirstData()); break; @@ -678,6 +733,7 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { found = true; break; + case "NICKNAME": case "NICK-NAME": if (cur.firstChild === null) { break; @@ -686,23 +742,26 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { found = true; break; + // kolab 2+3 case "SMTP-ADDRESS": case "EMAIL": //synckolab.tools.logMessage("email: " + email + " - " + cur.getXmlResult("SMTP-ADDRESS", ""), synckolab.global.LOG_DEBUG + synckolab.global.LOG_AB); + var emailAddress = cur.getXmlResult("SMTP-ADDRESS", ""); + emailAddress += cur.getXmlResult("TEXT", ""); switch (email) { case 0: - this.setCardProperty(card, "PrimaryEmail", cur.getXmlResult("SMTP-ADDRESS", "")); + this.setCardProperty(card, "PrimaryEmail", emailAddress); // only applies to tbird < 3 if (card.defaultEmail) { card.defaultEmail = this.getCardProperty(card, "PrimaryEmail"); } break; case 1: - this.setCardProperty(card, "SecondEmail", cur.getXmlResult("SMTP-ADDRESS", "")); + this.setCardProperty(card, "SecondEmail", emailAddress); break; default: // remember other emails - this.setCardProperty(card, "EMAIL" + email, cur.getXmlResult("SMTP-ADDRESS", ""), true); + this.setCardProperty(card, "EMAIL" + email, emailAddress, true); break; } email++; @@ -723,10 +782,65 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { this.setCardProperty(card, "Company", cur.getFirstData()); found = true; break; + + + case "TEL": // kolab3 + num = cur.getFirstData(); + + // figure out the right type + var type = 0; // 0 = phone; 1 = mobile; 2 = fax; + var where = 0; // 0 = default; 1 = home; 2 = work + + var types = cur.getChildNode("parameters"); + if(types) { + types = types.getChildNode("type"); + if(types) { + types = types.getChildNode("text"); + while (types) { + switch(types.getFirstData()) { + case "home": where = 1; break; + case "work": where = 2; break; + case "cell": type = 1; break; + case "fax": type = 2; break; + case "pager": + case "page": + type = 3; break; + default: + synckolab.tools.logMessage("Unknown phone type: " + types.getXmlResult(), synckolab.global.LOG_INFO + synckolab.global.LOG_AB); + } + types = types.getNextNode("text"); + } + } + } + + switch(type) { + case 0: // phone + switch(where) { + case 0: // def + case 1: // home + this.setCardProperty(card, "HomePhone", num); + break; + case 2: // work + this.setCardProperty(card, "WorkPhone", num); + break; + } + break; + case 1: // cell + this.setCardProperty(card, "CellularNumber", num); + break; + case 2: // fax + this.setCardProperty(card, "FaxNumber", num); + break; + case 3: + this.setCardProperty(card, "PagerNumber", num); + break; + } + found = true; + break; - // these two are the same - case "PHONE": - var num = cur.getXmlResult("NUMBER", ""); + + case "PHONE": // kolab2 + num = cur.getXmlResult("NUMBER", ""); switch (cur.getXmlResult("TYPE", "CELLULAR").toUpperCase()) { case "MOBILE": case "CELLULAR": @@ -755,17 +869,31 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { found = true; break; - case "BIRTHDAY": + case "BDAY": // kolab3 + case "BIRTHDAY": // kolab2 if (cur.firstChild === null) { break; } - tok = cur.firstChild.data.split("-"); - this.setCardProperty(card, "BirthYear", tok[0]); - if(tok.length > 2) { - this.setCardProperty(card, "BirthMonth", tok[1]); - // BDAY: 1987-09-27 - this.setCardProperty(card, "BirthDay", tok[2]); + + tok = cur.getChildNode("date-time"); + // get the data from the date-time node + if(tok) { + tok = tok.getFirstData(); + } else { + // get from date node + tok = cur.getChildNode("date"); + if(tok) { + tok = tok.getFirstData(); + } else { + tok = cur.getFirstData(); + } } + // convert to date + tok = synckolab.tools.text.string2DateTime(tok); + + this.setCardProperty(card, "BirthYear", tok.getFullYear()); + this.setCardProperty(card, "BirthMonth", tok.getMonth()); + this.setCardProperty(card, "BirthDay", tok.getDate()); found = true; break; // anniversary - not in vcard rfc?? @@ -773,23 +901,80 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { if (cur.firstChild === null) { break; } - tok = cur.getFirstData().split("-"); - this.setCardProperty(card, "AnniversaryYear", tok[0]); - if(tok.length > 2) { - this.setCardProperty(card, "AnniversaryMonth", tok[1]); - // BDAY:1987-09-27T08:30:00-06:00 - this.setCardProperty(card, "AnniversaryDay", tok[2]); + tok = cur.getChildNode("date-time"); + // get the data from the date-time node + if(tok) { + tok = tok.getFirstData(); + } else { + // get from date node + tok = cur.getChildNode("date"); + if(tok) { + tok = tok.getFirstData(); + } else { + tok = cur.getFirstData(); + } + } + // convert to date + tok = synckolab.tools.text.string2DateTime(tok); + + this.setCardProperty(card, "AnniversaryYear", tok.getFullYear()); + this.setCardProperty(card, "AnniversaryMonth", tok.getMonth()); + this.setCardProperty(card, "AnniversaryDay", tok.getDate()); + found = true; + break; + + case "ADR": // kolab3 + // figure out the right type + var where = 0; // 0 = default; 1 = home; 2 = work + var types = cur.getChildNode("parameters"); + if(types) { + types = types.getChildNode("type"); + if(types) { + types = types.getChildNode("text"); + while (types) { + switch(types.getFirstData()) { + case "home": where = 1; break; + case "work": where = 2; break; + default: + synckolab.tools.logMessage("Unknown adr type: " + types.getXmlResult(), synckolab.global.LOG_INFO + synckolab.global.LOG_AB); + } + types = types.getNextNode("text"); + } + } + } + + // now fill accordingly + switch(where) { + case 0: + case 1: + this.setCardProperty(card, "HomeAddress", cur.getXmlResult("STREET", "")); + this.setCardProperty(card, "HomeAddress2", cur.getXmlResult("STREET2", "")); + this.setCardProperty(card, "HomeCity", cur.getXmlResult("LOCALITY", "")); + this.setCardProperty(card, "HomeState", cur.getXmlResult("REGION", "")); + this.setCardProperty(card, "HomeZipCode", cur.getXmlResult("CODE", "")); + this.setCardProperty(card, "HomeCountry", cur.getXmlResult("COUNTRY", "")); + break; + case 2: + this.setCardProperty(card, "WorkAddress", cur.getXmlResult("STREET", "")); + this.setCardProperty(card, "WorkAddress2", cur.getXmlResult("STREET2", "")); + this.setCardProperty(card, "WorkCity", cur.getXmlResult("LOCALITY", "")); + this.setCardProperty(card, "WorkState", cur.getXmlResult("REGION", "")); + this.setCardProperty(card, "WorkZipCode", cur.getXmlResult("CODE", "")); + this.setCardProperty(card, "WorkCountry", cur.getXmlResult("COUNTRY", "")); + break; } found = true; + break; + /* @deprecated case "PREFERRED-ADDRESS": if (cur.firstChild) this.setCardProperty(card, "DefaultAddress", cur.getFirstData()); break; */ - case "ADDRESS": + case "ADDRESS": //kolab2 switch (cur.getXmlResult("TYPE", "HOME").toUpperCase()) { case "HOME": this.setCardProperty(card, "HomeAddress", cur.getXmlResult("STREET", "")); @@ -832,7 +1017,9 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { this.setCardProperty(card, "PhotoURI", uri); } break; - case "BODY": + + case "NOTE": // kolab3 + case "BODY": // kolab2 if (cur.firstChild === null) { break; } @@ -850,27 +1037,37 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { found = true; break; - case "WEB-PAGE": + case "URL": //kolab3 if (cur.firstChild === null) { break; } - this.setCardProperty(card, "WebPage1", cur.getFirstData()); + var value = cur.getXmlResult("URI", ""); + + if(!card.WebPage1 || card.WebPage1 === "") { + this.setCardProperty(card, "WebPage1", value); + } else if(!card.WebPage2 || card.WebPage2 === "") { + this.setCardProperty(card, "WebPage2", value); + } else if(!card.WebPage3 || card.WebPage3 === "") { + this.setCardProperty(card, "WebPage3", value); + } + found = true; break; - - case "BUSINESS-WEB-PAGE": + case "WEB-PAGE": // kolab2 if (cur.firstChild === null) { break; } - this.setCardProperty(card, "WebPage2", cur.getFirstData()); + value = cur.getFirstData(); + this.setCardProperty(card, "WebPage1", value); found = true; break; - case "UID": + case "BUSINESS-WEB-PAGE": if (cur.firstChild === null) { break; } - this.setUID(card, cur.getFirstData()); + this.setCardProperty(card, "WebPage2", cur.getFirstData()); + found = true; break; case "CUSTOM1": @@ -900,6 +1097,7 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { this.setCardProperty(card, "Custom4", cur.getFirstData()); break; + case "IMPP": case "IM-ADDRESS": if (cur.firstChild === null) { break; @@ -913,8 +1111,26 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { } this.setCardProperty(card, "AllowRemoteContent", 'TRUE' === cur.firstChild.data.toUpperCase()); break; + + case "X-CUSTOM": // kolab3 + // dunno if we need to support this + break; + case "PHOTO": // kolab3 + // handle photo VERY special... TODO + break; + case "GROUP": + // should wehandle this? + break; + // fields we know and can skip + case "PRODID": + case "KIND": + case "X-KOLAB-VERSION": + break; + - // fields we "know" about but just cannot work with (used for kolab 3) + // fields we "know" about but just cannot work with + case "RELATED": //kolab3 + case "TITLE": case "CREATION-DATE": case "LATITUDE": case "LONGITUDE": @@ -938,7 +1154,7 @@ synckolab.addressbookTools.xml2Card = function (xml, card) { } if (cur.nodeName !== "product-id" && cur.nodeName !== "sensitivity") { // remember other fields - synckolab.tools.logMessage("FIELD not found: " + cur.nodeName + "=" + cur.getFirstData(), synckolab.global.LOG_WARNING + synckolab.global.LOG_AB); + synckolab.tools.logMessage("FIELD not found: '" + cur.nodeName + "' firstData='" + cur.getFirstData()+"'", synckolab.global.LOG_WARNING + synckolab.global.LOG_AB); this.setCardProperty(card, cur.nodeName, cur.getFirstData(), true); } break; diff --git a/src/chrome/content/synckolab/config.js b/src/chrome/content/synckolab/config.js index 4eef754..0902159 100644 --- a/src/chrome/content/synckolab/config.js +++ b/src/chrome/content/synckolab/config.js @@ -64,7 +64,7 @@ synckolab.config = { // automatically sync every X minutes (0 = disable) //@deprecated syncInterval: {type: synckolab.tools.CONFIG_TYPE_INT, def: 0 }, // format to use: xml|vcard - format: {type: synckolab.tools.CONFIG_TYPE_CHAR, def: "xml" }, + format: {type: synckolab.tools.CONFIG_TYPE_CHAR, def: "xml-k3" }, // timeframe to sync in (don't sync entries with an older start-date) timeFrame: {type: synckolab.tools.CONFIG_TYPE_INT, def: 180}, // enable the sync listener @@ -179,6 +179,12 @@ synckolab.config.loadAccountConfig = function (pref, acct) { synckolab.config.baseSetting[n].def); } } + + // Some fixes for old version + if(cConf.format && cConf.format.toLowerCase() === "xml") { + synckolab.tools.logMessage("Old config - autofixing xml->kolab2", synckolab.global.LOG_INFO); + cConf.format = "xml-k2"; + } } } } diff --git a/src/chrome/content/synckolab/tools.js b/src/chrome/content/synckolab/tools.js index bbcfbb3..73f647f 100644 --- a/src/chrome/content/synckolab/tools.js +++ b/src/chrome/content/synckolab/tools.js @@ -304,18 +304,21 @@ stripMailHeader: function (skcontent) { } // try to get the start of the card part - // remove the tmp image if it exists... - var file = Components.classes["@mozilla.org/file/directory_service;1"].getService(Components.interfaces.nsIProperties).get("TmpD", Components.interfaces.nsIFile); - file.append("syncKolab.img"); - if (file.exists()) { - file.remove(true); + // remove the tmp image if it exists (only in xul environment)... + if (typeof Components !== "undefined") { + var file = Components.classes["@mozilla.org/file/directory_service;1"].getService(Components.interfaces.nsIProperties).get("TmpD", Components.interfaces.nsIFile); + file.append("syncKolab.img"); + if (file.exists()) { + file.remove(true); + } } // check if we have an image attachment var imgC = skcontent; var imgIdx = imgC.search(/Content-Type:[ \t\r\n]+image/i); - if (imgIdx !== -1) + // only works in xul environment + if (imgIdx !== -1 && typeof Components !== "undefined") { // get rid of the last part until the boundary imgC = imgC.substring(imgIdx); @@ -1317,10 +1320,26 @@ synckolab.Node = function (node) { this.nextSibling = new synckolab.Node(node.nextSibling); }; -synckolab.Node.prototype.getFirstData = function () { +/** + * return the data of the current node. this can either be + * the direct firstChild - or instead a text subnode + */ +synckolab.Node.prototype.getFirstData = function () { if (!this.node.firstChild) { return null; } + // we might have a "text" node (kolab3) + var text = this.getChildNode("text"); + if(text) { + return synckolab.tools.text.decode4XML(text.firstChild.data); + } + // uri is also handled like direct content + text = this.getChildNode("uri"); + if(text) { + return synckolab.tools.text.decode4XML(text.firstChild.data); + } + + // cur.nodeType === Node.TEXT_NODE return synckolab.tools.text.decode4XML(this.node.firstChild.data); }; @@ -1331,9 +1350,13 @@ synckolab.Node.prototype.getFirstData = function () { synckolab.Node.prototype.getXmlResult = function (name, def) { var cur = this.node.firstChild; + if(name) { + name = name.toUpperCase(); + } + while(cur) { - if (cur.nodeName.toUpperCase() === name.toUpperCase()) + if (cur.nodeName.toUpperCase() === name) { if (cur.hasChildNodes()) { @@ -1355,12 +1378,18 @@ synckolab.Node.prototype.getXmlResult = function (name, def) */ synckolab.Node.prototype.getChildNode = function (name) { + if(name) { + name = name.toUpperCase(); + } + var cur = this.node.firstChild; while(cur) { - if (cur.nodeName.toUpperCase() === name.toUpperCase()) - { - return cur; + if(cur.nodeType === Node.ELEMENT_NODE) { + if (cur.nodeName.toUpperCase() === name) + { + return new synckolab.Node(cur); + } } cur = cur.nextSibling; } @@ -1368,6 +1397,37 @@ synckolab.Node.prototype.getChildNode = function (name) }; /** + * returns the next sibling element of the current node. + * If a name is given it has to match + * @param name (option) name of the node to get + */ +synckolab.Node.prototype.getNextNode = function (name) +{ + if(name) { + name = name.toUpperCase(); + } + // start with the next node + var cur = this.node.nextSibling; + while(cur) + { + if(cur.nodeType === Node.ELEMENT_NODE) { + if (!name) { + return new synckolab.Node(cur); + } + else if (cur.nodeName.toUpperCase() === name) + { + return new synckolab.Node(cur); + } + } + // next sibling + cur = cur.nextSibling; + } + return null; +}; + + + +/** * return the value of the attribute with name "attrName" of the node "node" * or null, if no attribute with that name exists */ diff --git a/src/chrome/content/synckolab/tools/text.js b/src/chrome/content/synckolab/tools/text.js index eda4649..2058c25 100644 --- a/src/chrome/content/synckolab/tools/text.js +++ b/src/chrome/content/synckolab/tools/text.js @@ -220,36 +220,64 @@ synckolab.tools.text = { /** * ------ functions for date / string conversions ------------------------ */ - - // takes: 2005-03-30T15:28:52Z or 2005-03-30 15:28:52 - string2DateTime : function (val) { - // in case its a date without time - if (val.indexOf(":") === -1) { - return this.string2Date(val); - } - + + + // takes: 2005-03-30T15:28:52Z or 2005-03-30 15:28:52 or: 20050303T152852Z + string2DateTime : function (val, useUTC) { var s = val.replace('T', ' '); s = s.replace('Z', ''); var both = s.split(' '); - var cdate = both[0].split('-'); - var ctime = both[1].split(':'); - return new Date(cdate[0], cdate[1] - 1, cdate[2], ctime[0], ctime[1], ctime[2]); - + var cdate = both[0]; + // kolab2: 2005-03-30 + if(cdate.indexOf('-') !== -1) { + cdate = cdate.split('-'); + } else { + // kolab3: YYYYMMDD + cdate = []; + cdate[0] = both[0].substr(0,4); + if(both[0].length > 7) { + cdate[1] = both[0].substr(4,2); + cdate[2] = both[0].substr(6,2); + } else { + cdate[1] = 1; + cdate[2] = 1; + } + } + var ctime; + + if(both.length > 1) { + ctime = both[1]; + if(ctime.indexOf(':') !== -1) { + ctime = ctime.split(':'); + } else { + // kolab3: HHmmSS + ctime = []; + ctime[0] = both[1].substr(0,2); + ctime[1] = both[1].substr(2,2); + ctime[2] = both[1].substr(4,2); + } + if(useUTC) { + return new Date(Date.UTC(cdate[0], cdate[1] - 1, cdate[2], ctime[0], ctime[1], ctime[2])); + } + else { + return new Date(cdate[0], cdate[1] - 1, cdate[2], ctime[0], ctime[1], ctime[2]); + } + } + else { + if(useUTC) { + return new Date(Date.UTC(cdate[0], cdate[1] - 1, cdate[2])); + } + else { + return new Date(cdate[0], cdate[1] - 1, cdate[2]); + } + } }, // takes: 2005-03-30T15:28:52Z or 2005-03-30 15:28:52 string2CalDateTime : function (val, useUTC) { // in case its a date without time fall back to string2CalDate() - if (val.indexOf(":") === -1) { - return this.string2CalDate(val); - } - - var s = val.replace('T', ' '); - s = s.replace('Z', ''); - var both = s.split(' '); - var cdate = both[0].split('-'); - var ctime = both[1].split(':'); - var calDateTime = null; + var calDateTime; + // lightning 0.9pre fix (uses createDateTime) if (typeof createDateTime !== 'undefined') { calDateTime = new createDateTime(); @@ -261,79 +289,64 @@ synckolab.tools.text = { var jsDate = null; if (useUTC) { - jsDate = new Date(Date.UTC(cdate[0], cdate[1] - 1, cdate[2], ctime[0], ctime[1], ctime[2])); + jsDate = this.string2DateTime(val, true); } else { - jsDate = new Date(cdate[0], cdate[1] - 1, cdate[2], ctime[0], ctime[1], ctime[2]); + jsDate = this.string2DateTime(val); } + calDateTime.jsDate = jsDate; return calDateTime; }, // produces: 2005-03-30 - date2String : function (datetime, normal) { + date2String : function (datetime, normal, compact) { if (!datetime) { return ''; } - if (normal) { - return datetime.getFullYear() + "-" + (datetime.getMonth() + 1 < 10 ? "0" : "") + (datetime.getMonth() + 1) + "-" + (datetime.getDate() < 10 ? "0" : "") + datetime.getDate(); - } else { - return datetime.getUTCFullYear() + "-" + (datetime.getUTCMonth() + 1 < 10 ? "0" : "") + (datetime.getUTCMonth() + 1) + "-" + (datetime.getUTCDate() < 10 ? "0" : "") + datetime.getUTCDate(); + if (compact) { + if (normal) { + return datetime.getFullYear() + (datetime.getMonth() + 1 < 10 ? "0" : "") + (datetime.getMonth() + 1) + (datetime.getDate() < 10 ? "0" : "") + datetime.getDate(); + } else { + return datetime.getUTCFullYear() + (datetime.getUTCMonth() + 1 < 10 ? "0" : "") + (datetime.getUTCMonth() + 1) + (datetime.getUTCDate() < 10 ? "0" : "") + datetime.getUTCDate(); + } + } else { + if (normal) { + return datetime.getFullYear() + "-" + (datetime.getMonth() + 1 < 10 ? "0" : "") + (datetime.getMonth() + 1) + "-" + (datetime.getDate() < 10 ? "0" : "") + datetime.getDate(); + } else { + return datetime.getUTCFullYear() + "-" + (datetime.getUTCMonth() + 1 < 10 ? "0" : "") + (datetime.getUTCMonth() + 1) + "-" + (datetime.getUTCDate() < 10 ? "0" : "") + datetime.getUTCDate(); + } } }, // produces 15:28:52 - time2String : function (datetime) { + time2String : function (datetime, compact) { + if(compact) { + return (datetime.getUTCHours() < 10 ? "0" : "") + datetime.getUTCHours() + (datetime.getUTCMinutes() < 10 ? "0" : "") + datetime.getUTCMinutes() + (datetime.getUTCSeconds() < 10 ? "0" : "") + datetime.getUTCSeconds(); + } return (datetime.getUTCHours() < 10 ? "0" : "") + datetime.getUTCHours() + ":" + (datetime.getUTCMinutes() < 10 ? "0" : "") + datetime.getUTCMinutes() + ":" + (datetime.getUTCSeconds() < 10 ? "0" : "") + datetime.getUTCSeconds(); }, // produces: 2005-03-30T15:28:52Z for allday = false, // produces: 2005-03-30 for allday = true - calDateTime2String : function (val, allday) { + calDateTime2String : function (val, allday, compact) { if (val === null) { return ""; } - var datetime = (val instanceof Date) ? val : val.jsDate; + var datetime = val.jsDate ? val.jsDate: val; //alert("EVENT TIME: " + datetime); // make sure not to use UTC for all-day events - var resultstring = this.date2String(datetime, allday); + var resultstring = this.date2String(datetime, allday, compact); if (!allday) { resultstring += 'T'; - resultstring += this.time2String(datetime); + resultstring += this.time2String(datetime, compact); resultstring += 'Z'; } return resultstring; }, - // takes: 2005-03-30 - string2Date : function (val) { - var s = val.replace('T', ''); - var cdate = s.split('-'); - return new Date(cdate[0], cdate[1] - 1, cdate[2]); - }, - - // takes: 2005-03-30 - string2CalDate : function (val) { - var s = val.replace('T', ''); - var cdate = s.split('-'); - var calDateTime = null; - - // lightning 0.9pre fix (uses createDateTime) - if (typeof createDateTime !== 'undefined') { - calDateTime = new createDateTime(); - } else if (CalDateTime) { - calDateTime = new CalDateTime(); - } else { - calDateTime = Components.classes["@mozilla.org/calendar/datetime;1"].createInstance(Components.interfaces.calIDateTime); - } - - calDateTime.jsDate = new Date(Date.UTC(cdate[0], cdate[1] - 1, cdate[2], 0, 0, 0)); - calDateTime.isDate = true; - return calDateTime; - }, - // Create a duration object for an alarm time createDuration : function (minutes) { var duration = Components.classes["@mozilla.org/calendar/duration;1"].createInstance(Components.interfaces.calIDuration); @@ -738,6 +751,114 @@ synckolab.tools.text.quoted = { } }; +synckolab.tools.text.uu = { + encode: function(str) { + throw("UUEncode not implemented"); + }, + + decode: function(str) { + // http://kevin.vanzonneveld.net + // + original by: Ole Vrijenhoek + // + bugfixed by: Brett Zamir (http://brett-zamir.me) + // - depends on: is_scalar + // - depends on: rtrim + // * example 1: convert_uudecode('+22!L;W9E(%!(4\"$`\n`'); + // * returns 1: 'I love PHP' + + // Not working perfectly + + // shortcut + var chr = function (c) { + return String.fromCharCode(c); + }; + + if (!str || str=="") { + return chr(0); + } else if (!this.is_scalar(str)) { + return false; + } else if (str.length < 8) { + return false; + } + + var decoded = "", tmp1 = "", tmp2 = ""; + var c = 0, i = 0, j = 0, a = 0; + var line = str.split("\n"); + var bytes = []; + + for (i in line) { + c = line[i].charCodeAt(0); + bytes = line[i].substr(1); + + // Convert each char in bytes[] to a 6-bit + for (j in bytes) { + tmp1 = bytes[j].charCodeAt(0)-32; + tmp1 = tmp1.toString(2); + while (tmp1.length < 6) { + tmp1 = "0" + tmp1; + } + tmp2 += tmp1 + } + + for (i=0; i<=(tmp2.length/8)-1; i++) { + tmp1 = tmp2.substr(a, 8); + if (tmp1 == "01100000") { + decoded += this.chr(0); + } else { + decoded += this.chr(parseInt(tmp1, 2)); + } + a += 8; + } + a = 0; + tmp2 = ""; + } + return this.rtrim(decoded, "\0"); + }, + + rtrim: function (str, charlist) { + // http://kevin.vanzonneveld.net + // + original by: Kevin van Zonneveld (http://kevin.vanzonneveld.net) + // + input by: Erkekjetter + // + improved by: Kevin van Zonneveld (http://kevin.vanzonneveld.net) + // + bugfixed by: Onno Marsman + // + input by: rem + // + bugfixed by: Brett Zamir (http://brett-zamir.me) + // * example 1: rtrim(' Kevin van Zonneveld '); + // * returns 1: ' Kevin van Zonneveld' + charlist = !charlist ? ' \\s\u00A0' : (charlist + '').replace(/([\[\]\(\)\.\?\/\*\{\}\+\$\^\:])/g, '\\$1'); + var re = new RegExp('[' + charlist + ']+$', 'g'); + return (str + '').replace(re, ''); + }, + + is_scalar: function(mixed_var) { + // http://kevin.vanzonneveld.net + // + original by: Paulo Freitas + // * example 1: is_scalar(186.31); + // * returns 1: true + // * example 2: is_scalar({0: 'Kevin van Zonneveld'}); + // * returns 2: false + return (/boolean|number|string/).test(typeof mixed_var); + }, + + chr: function (codePt) { + // http://kevin.vanzonneveld.net + // + original by: Kevin van Zonneveld (http://kevin.vanzonneveld.net) + // + improved by: Brett Zamir (http://brett-zamir.me) + // * example 1: chr(75); + // * returns 1: 'K' + // * example 1: chr(65536) === '\uD800\uDC00'; + // * returns 1: true + if (codePt > 0xFFFF) { // Create a four-byte string (length 2) since this code point is high + // enough for the UTF-16 encoding (JavaScript internal use), to + // require representation with two surrogates (reserved non-characters + // used for building other characters; the first is "high" and the next "low") + codePt -= 0x10000; + return String.fromCharCode(0xD800 + (codePt >> 10), 0xDC00 + (codePt & 0x3FF)); + } + return String.fromCharCode(codePt); + } + + +} /** * Base 64 decoder * Usage: @@ -795,3 +916,5 @@ synckolab.tools.text.base64 = { return result; } }; + + diff --git a/src/chrome/content/synckolab/wndConfig.js b/src/chrome/content/synckolab/wndConfig.js index 2c5f6db..a29425a 100644 --- a/src/chrome/content/synckolab/wndConfig.js +++ b/src/chrome/content/synckolab/wndConfig.js @@ -231,10 +231,16 @@ synckolab.settings.init = function () { abchild = document.createElement("menuitem"); abpopup.appendChild(abchild); abchild.setAttribute("label", "Xml/Kolab2"); - abchild.setAttribute("value", "Xml"); + abchild.setAttribute("value", "xml-k2"); + + abchild = document.createElement("menuitem"); + abpopup.appendChild(abchild); + abchild.setAttribute("label", "Xml/Kolab3"); + abchild.setAttribute("value", "xml-k3"); abchild.setAttribute("selected", "true"); - abList.setAttribute("label", "Xml/Kolab2"); - abList.setAttribute("value", "Xml"); + + abList.setAttribute("label", "Xml/Kolab3"); + abList.setAttribute("value", "xml-k3"); abList = document.getElementById("calendarFormat"); abpopup = document.createElement("menupopup"); @@ -247,10 +253,16 @@ synckolab.settings.init = function () { abchild = document.createElement("menuitem"); abpopup.appendChild(abchild); abchild.setAttribute("label", "Xml/Kolab2"); - abchild.setAttribute("value", "Xml"); + abchild.setAttribute("value", "xml-k2"); + + abchild = document.createElement("menuitem"); + abpopup.appendChild(abchild); + abchild.setAttribute("label", "Xml/Kolab3"); + abchild.setAttribute("value", "xml-k3"); abchild.setAttribute("selected", "true"); - abList.setAttribute("label", "Xml/Kolab2"); - abList.setAttribute("value", "Xml"); + + abList.setAttribute("label", "Xml/Kolab3"); + abList.setAttribute("value", "xml-k3"); abList = document.getElementById("taskFormat"); abpopup = document.createElement("menupopup"); @@ -263,10 +275,16 @@ synckolab.settings.init = function () { abchild = document.createElement("menuitem"); abpopup.appendChild(abchild); abchild.setAttribute("label", "Xml/Kolab2"); - abchild.setAttribute("value", "Xml"); + abchild.setAttribute("value", "xml-k2"); + + abchild = document.createElement("menuitem"); + abpopup.appendChild(abchild); + abchild.setAttribute("label", "Xml/Kolab3"); + abchild.setAttribute("value", "xml-k3"); abchild.setAttribute("selected", "true"); - abList.setAttribute("label", "Xml/Kolab2"); - abList.setAttribute("value", "Xml"); + + abList.setAttribute("label", "Xml/Kolab3"); + abList.setAttribute("value", "xml-k3"); // the adress book list // fill the contact selection |