summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorniko <niko>2012-10-06 23:25:33 (GMT)
committerniko <niko>2012-10-06 23:25:33 (GMT)
commit1b345176e3942b5909862878e772bfe83b6c9f94 (patch)
tree93b84269eff1e5d244887d193415ba80f2ab72bd /src
parent32c1661206a070f04a15fc024464f91e932aac35 (diff)
downloadsynckolab-1b345176e3942b5909862878e772bfe83b6c9f94.tar.gz
reading of kolab3 format - unit tests
Diffstat (limited to 'src')
-rw-r--r--src/chrome/content/synckolab/addressbookTools.js288
-rw-r--r--src/chrome/content/synckolab/config.js8
-rw-r--r--src/chrome/content/synckolab/tools.js82
-rw-r--r--src/chrome/content/synckolab/tools/text.js245
-rw-r--r--src/chrome/content/synckolab/wndConfig.js36
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