Bug 340949, 368820, 356125: minding signons.rememberSignons, simple caching, using search_calprops, email alarms, misc cleanup

This commit is contained in:
daniel.boelzle%sun.com 2007-02-02 14:41:16 +00:00
Родитель e8f0f42c9f
Коммит 145168b40b
10 изменённых файлов: 415 добавлений и 358 удалений

Просмотреть файл

@ -103,14 +103,14 @@ calWcapCachedCalendar.prototype = {
get remoteCal() {
return this.m_remoteCal;
},
set remoteCal( cal ) {
set remoteCal(cal) {
if (this.m_remoteCal != null)
this.m_remoteCal.removeObserver( this.m_observerMultiplexer );
if (cal != null) {
cal.addObserver( this.m_observerMultiplexer );
cal.superCalendar = this;
}
this.m_remoteCal = cal;
return (this.m_remoteCal = cal);
},
getCalKey:
@ -156,12 +156,12 @@ calWcapCachedCalendar.prototype = {
}
return this.m_localCal;
},
set localCal( cal ) {
set localCal(cal) {
if (cal != null) {
cal.suppressAlarms = this.remoteCal.suppressAlarms; // sync setting
cal.superCalendar = this;
}
this.m_localCal = cal;
return (this.m_localCal = cal);
},
toString:
@ -213,9 +213,9 @@ calWcapCachedCalendar.prototype = {
get session() { return this.remoteCal.session; },
get calId() { return this.remoteCal.calId; },
get calId_() { return this.remoteCal.calId_; },
set calId( id ) {
set calId(id) {
this.localCal = null; // disconnect
this.remoteCal.calId = id;
return (this.remoteCal.calId = id);
},
get description() { return this.remoteCal.description; },
get displayName() { return this.remoteCal.displayName; },
@ -236,25 +236,26 @@ calWcapCachedCalendar.prototype = {
get name() {
return getCalendarManager().getCalendarPref( this, "NAME" );
},
set name( name ) {
set name(name) {
getCalendarManager().setCalendarPref( this, "NAME", name );
return name;
},
get type() { return "wcap"; },
m_bReadOnly: false,
get readOnly() { return (this.m_bReadOnly || this.remoteCal.readOnly); },
set readOnly( bReadOnly ) { this.m_bReadOnly = bReadOnly; },
set readOnly(bReadOnly) { return (this.m_bReadOnly = bReadOnly); },
get uri() { return this.remoteCal.uri; },
set uri( thatUri ) {
set uri(thatUri) {
this.localCal = null; // disconnect
this.remoteCal.uri = thatUri;
return (this.remoteCal.uri = thatUri);
},
m_superCalendar: null,
get superCalendar() { return this.m_superCalendar || this; },
set superCalendar( cal ) { this.m_superCalendar = cal; },
set superCalendar(cal) { return (this.m_superCalendar = cal); },
m_observers: null,
notifyObservers:
@ -294,7 +295,7 @@ calWcapCachedCalendar.prototype = {
get suppressAlarms() { return this.remoteCal.suppressAlarms; },
set suppressAlarms( bSuppressAlarms ) {
this.remoteCal.suppressAlarms = bSuppressAlarms;
this.localCal.suppressAlarms = this.remoteCal.suppressAlarms;
return (this.localCal.suppressAlarms = this.remoteCal.suppressAlarms);
},
get canRefresh() { return true; },
@ -347,10 +348,10 @@ calWcapCachedCalendar.prototype = {
},
getItems:
function( itemFilter, maxResult, rangeStart, rangeEnd, listener )
function( itemFilter, maxResults, rangeStart, rangeEnd, listener )
{
this.log( "getItems():\n\titemFilter=" + itemFilter +
",\n\tmaxResult=" + maxResult +
",\n\tmaxResults=" + maxResults +
",\n\trangeStart=" + getIcalUTC(rangeStart) +
",\n\trangeEnd=" + getIcalUTC(rangeEnd) );
var this_ = this;
@ -360,11 +361,11 @@ calWcapCachedCalendar.prototype = {
function( calendar, status, opType, id, detail )
{
if (listener != null) {
if (status == Components.results.NS_OK) {
if (status == NS_OK) {
// delegate to local cal:
this_.log("begin localCal.getItems().");
this_.localCal.getItems(
itemFilter, maxResult, rangeStart, rangeEnd,
itemFilter, maxResults, rangeStart, rangeEnd,
listener );
this_.log("end localCal.getItems().");
}
@ -476,7 +477,7 @@ calWcapCachedCalendar.prototype = {
function( calendar, status, opType, id, detail )
{
try {
if (status == Components.results.NS_OK) {
if (status == NS_OK) {
if (opType == SYNC) {
// write stamp: only if necessary
if (dtFrom == null ||
@ -486,8 +487,7 @@ calWcapCachedCalendar.prototype = {
if (listener != null) {
listener.onOperationComplete(
this_.superCalendar,
Components.results.NS_OK,
SYNC, null, null );
NS_OK, SYNC, null, null );
}
}
else {

Просмотреть файл

@ -123,14 +123,16 @@ calWcapCalendar.prototype = {
str += ", default calendar";
return str;
},
notifyError: function calWcapCalendar_notifyError(err)
notifyError: function calWcapCalendar_notifyError(err, suppressOnError)
{
debugger;
var msg = logError(err, this);
this.notifyObservers(
"onError",
err instanceof Components.interfaces.nsIException
? [err.result, err.message] : [isNaN(err) ? -1 : err, msg] );
if (!suppressOnError) {
this.notifyObservers(
"onError",
err instanceof Components.interfaces.nsIException
? [err.result, err.message] : [isNaN(err) ? -1 : err, msg]);
}
},
// calICalendarProvider:
@ -156,13 +158,18 @@ calWcapCalendar.prototype = {
set name( name ) {
getCalendarManager().setCalendarPref(
this.session.defaultCalendar, "NAME", name);
return name;
},
get type() { return "wcap"; },
m_superCalendar: null,
get superCalendar() { return this.m_superCalendar || this; },
set superCalendar( cal ) { this.m_superCalendar = cal; },
get superCalendar() {
return (this.m_superCalendar || this);
},
set superCalendar(cal) {
return (this.m_superCalendar = cal);
},
m_bReadOnly: false,
get readOnly() {
@ -175,7 +182,7 @@ calWcapCalendar.prototype = {
!this.checkAccess(calIWcapCalendar.AC_COMP_WRITE));
},
set readOnly(bReadOnly) {
this.m_bReadOnly = bReadOnly;
return (this.m_bReadOnly = bReadOnly);
},
get uri() {
@ -187,8 +194,8 @@ calWcapCalendar.prototype = {
else
return this.session.uri;
},
set uri( thatUri ) {
this.session.uri = thatUri;
set uri(thatUri) {
return (this.session.uri = thatUri);
},
notifyObservers: function calWcapCalendar_notifyObservers(func, args) {
@ -225,12 +232,14 @@ calWcapCalendar.prototype = {
(this.session.isLoggedIn && !this.isOwnedCalendar));
},
set suppressAlarms(bSuppressAlarms) {
this.m_bSuppressAlarms = bSuppressAlarms;
return (this.m_bSuppressAlarms = bSuppressAlarms);
},
get canRefresh() { return false; },
get canRefresh() { return (this.m_cachedResults != null); },
refresh: function calWcapCalendar_refresh() {
log("refresh.", this);
// invalidate cached results:
delete this.m_cachedResults;
},
issueNetworkRequest: function calWcapCalendar_issueNetworkRequest(

Просмотреть файл

@ -65,6 +65,51 @@ function calWcapCalendar_encodeAttendee(att)
return encodeAttr(att.id, null, params);
};
calWcapCalendar.prototype.getRecurrenceParams =
function calWcapCalendar_getRecurrenceParams(
item, out_rrules, out_rdates, out_exrules, out_exdates)
{
// recurrences:
out_rrules.value = [];
out_rdates.value = [];
out_exrules.value = [];
out_exdates.value = [];
if (item.recurrenceInfo) {
var rItems = item.recurrenceInfo.getRecurrenceItems({});
for each (var rItem in rItems) {
var isNeg = rItem.isNegative;
if (rItem instanceof Components.interfaces.calIRecurrenceRule) {
var rule = ("\"" + encodeURIComponent(
rItem.icalProperty.valueAsIcalString) +
"\"");
if (isNeg)
out_exrules.value.push(rule);
else
out_rrules.value.push(rule);
}
else if (rItem instanceof Components.interfaces.calIRecurrenceDateSet) {
var d = rItem.getDates({});
for each (var d in rdates) {
if (isNeg)
out_exdates.value.push( getIcalUTC(d.date) );
else
out_rdates.value.push( getIcalUTC(d.date) );
}
}
else if (rItem instanceof Components.interfaces.calIRecurrenceDate) {
if (isNeg)
out_exdates.value.push( getIcalUTC(rItem.date) );
else
out_rdates.value.push( getIcalUTC(rItem.date) );
}
else {
this.notifyError("don\'t know how to handle this recurrence item: " +
rItem.valueAsIcalString);
}
}
}
};
calWcapCalendar.prototype.encodeRecurrenceParams =
function calWcapCalendar_encodeRecurrenceParams(item, oldItem)
{
@ -95,21 +140,21 @@ function calWcapCalendar_encodeRecurrenceParams(item, oldItem)
var exdates_ = {};
this.getRecurrenceParams(oldItem, rrules_, rdates_, exrules_, exdates_);
function sameSet( list, list_ ) {
function sameSet(list, list_) {
return (list.length == list_.length &&
list.every( function(x) {
list.every( function everyFunc(x) {
return list_.some(
function(y) { return x == y; } );
function someFunc(y) { return x == y; } );
}
));
}
if (sameSet( rrules.value, rrules_.value ))
if (sameSet(rrules.value, rrules_.value))
rrules.value = null; // don't write
if (sameSet( rdates.value, rdates_.value ))
if (sameSet(rdates.value, rdates_.value))
rdates.value = null; // don't write
if (sameSet( exrules.value, exrules.value ))
if (sameSet(exrules.value, exrules.value))
exrules.value = null; // don't write
if (sameSet( exdates.value, exdates_.value ))
if (sameSet(exdates.value, exdates_.value))
exdates.value = null; // don't write
}
@ -123,13 +168,13 @@ function calWcapCalendar_encodeRecurrenceParams(item, oldItem)
return ret;
}
var ret = "";
if (rrules.value != null)
if (rrules.value)
ret += ("&rrules=" + encodeList(rrules.value));
if (rdates.value != null)
if (rdates.value)
ret += ("&rdates=" + encodeList(rdates.value));
if (exrules.value != null)
if (exrules.value)
ret += ("&exrules=" + encodeList(exrules.value));
if (exdates.value != null)
if (exdates.value)
ret += ("&exdates=" + encodeList(exdates.value));
return ret;
// xxx todo:
@ -139,52 +184,42 @@ function calWcapCalendar_encodeRecurrenceParams(item, oldItem)
// if rchange=0 is set!
};
calWcapCalendar.prototype.getRecurrenceParams =
function calWcapCalendar_getRecurrenceParams(
item, out_rrules, out_rdates, out_exrules, out_exdates)
calWcapCalendar.prototype.getAlarmParams =
function calWcapCalendar_getAlarmParams(item)
{
// recurrences:
out_rrules.value = [];
out_rdates.value = [];
out_exrules.value = [];
out_exdates.value = [];
if (item.recurrenceInfo) {
var rItems = item.recurrenceInfo.getRecurrenceItems({});
for each ( var rItem in rItems ) {
var isNeg = rItem.isNegative;
// xxx todo: need to QueryInterface() here?
if (rItem instanceof Components.interfaces.calIRecurrenceRule) {
var rule = ("\"" + encodeURIComponent(
rItem.icalProperty.valueAsIcalString) +
"\"");
if (isNeg)
out_exrules.value.push( rule );
else
out_rrules.value.push( rule );
}
// xxx todo: need to QueryInterface() here?
else if (rItem instanceof Components.interfaces.calIRecurrenceDateSet) {
var d = rItem.getDates({});
for each ( var d in rdates ) {
if (isNeg)
out_exdates.value.push( getIcalUTC(d.date) );
else
out_rdates.value.push( getIcalUTC(d.date) );
}
}
// xxx todo: need to QueryInterface() here?
else if (rItem instanceof Components.interfaces.calIRecurrenceDate) {
if (isNeg)
out_exdates.value.push( getIcalUTC(rItem.date) );
else
out_rdates.value.push( getIcalUTC(rItem.date) );
}
else {
this.notifyError("don\'t know how to handle this recurrence item: " +
rItem.valueAsIcalString);
}
var params = null;
var alarmStart = item.alarmOffset;
if (alarmStart) {
if (item.alarmRelated == calIItemBase.ALARM_RELATED_END) {
// cs does not support explicit RELATED=END when
// both start|entry and end|due are written
var dur = item.duration;
if (dur) { // both given
alarmStart = alarmStart.clone();
alarmStart.addDuration(dur);
} // else only end|due is set, alarm makes little sense though
}
var emails = "";
if (item.hasProperty("alarmEmailAddress"))
emails = encodeURIComponent(item.getProperty("alarmEmailAddress"));
else {
this.session.getDefaultAlarmEmails({}).forEach(
function forEachFunc(email) {
if (emails.length > 0)
emails += ";";
emails += encodeURIComponent(email);
});
}
if (emails.length > 0) {
params = ("&alarmStart=" + alarmStart.icalString);
params += ("&alarmEmails=" + emails);
}
// else popup
}
if (!params) // clear popup, email alarm:
params = "&alarmStart=&alarmPopup=&alarmEmails=";
return params;
};
// why ever, X-S1CS-EMAIL is unsupported though documented
@ -225,15 +260,22 @@ function equalDatetimes(one, two) {
return ((!one && !two) || (one && two && one.compare(two) == 0));
}
// @return null if nothing has changed else value to be written
function diffProperty(newItem, oldItem, propName) {
var val = null;
if (newItem.hasProperty(propName))
val = newItem.getProperty(propName);
if (oldItem && oldItem.hasProperty(propName)) {
if (!val) // property has been deleted
val = "";
else if (val == oldItem.getProperty(propName))
val = null;
if (oldItem) {
if (oldItem.hasProperty(propName)) {
if (!val) // property to be deleted
val = "";
else if (val == oldItem.getProperty(propName))
val = null; // property hasn't changed
}
}
else if (!val) {
// force value being set when no old item, eg when adding new item:
val = "";
}
return val;
}
@ -389,8 +431,8 @@ function calWcapCalendar_storeItem(bAddItem, item, oldItem, request, netRespFunc
dtstart = item.startDate;
var dtend = item.endDate;
bIsAllDay = (dtstart.isDate && dtend.isDate);
if (!oldItem || !equalDatetimes(dtstart, oldItem.startDate) ||
!equalDatetimes(dtend, oldItem.endDate)) {
if (!oldItem || !equalDatetimes(dtstart, oldItem.startDate)
|| !equalDatetimes(dtend, oldItem.endDate)) {
params += ("&dtstart=" + getIcalUTC(dtstart));
params += ("&X-NSCP-DTSTART-TZID=" +
"X-NSCP-ORIGINAL-OPERATION=X-NSCP-WCAP-PROPERTY-REPLACE^" +
@ -400,9 +442,6 @@ function calWcapCalendar_storeItem(bAddItem, item, oldItem, request, netRespFunc
"X-NSCP-ORIGINAL-OPERATION=X-NSCP-WCAP-PROPERTY-REPLACE^" +
encodeURIComponent(this.getAlignedTimezone(dtend.timezone)));
params += (bIsAllDay ? "&isAllDay=1" : "&isAllDay=0");
// // xxx todo: still needed?
// params += ("&tzid=" + encodeURIComponent(
// this.getAlignedTimezone(dtstart.timezone)));
}
}
else { // calITodo:
@ -452,11 +491,19 @@ function calWcapCalendar_storeItem(bAddItem, item, oldItem, request, netRespFunc
}
} // PUBLISH, REQUEST
var alarmParams = this.getAlarmParams(item);
if (!oldItem || (this.getAlarmParams(oldItem) != alarmParams)) {
if (bOrgRequest && params.length == 0) {
// assure no email notifications about this change:
params += "&smtp=0&smtpNotify=0";
}
params += alarmParams;
}
if (params.length == 0) {
log("no change at all.", this);
if (LOG_LEVEL > 2) {
log("old item:\n" + oldItem.icalString + "\n\nnew item:\n" +
item.icalString, this);
log("old item:\n" + oldItem.icalString + "\n\nnew item:\n" + item.icalString, this);
}
request.execRespFunc(null, item);
}
@ -468,17 +515,16 @@ function calWcapCalendar_storeItem(bAddItem, item, oldItem, request, netRespFunc
// WCAP_STORE_TYPE_CREATE, WCAP_STORE_TYPE_MODIFY
params += (bAddItem ? "&storetype=1" : "&storetype=2");
if (bIsParent) // THIS AND ALL INSTANCES:
params += "&mod=4";
if (bIsParent)
params += "&mod=4"; // THIS AND ALL INSTANCES
else {
// THIS INSTANCE:
var rid = item.recurrenceId;
if (rid.isDate) {
// cs does not accept DATE:
rid = rid.clone();
rid.isDate = false;
}
params += ("&mod=1&rid=" + getIcalUTC(rid));
params += ("&mod=1&rid=" + getIcalUTC(rid)); // THIS INSTANCE
}
if (bOrgRequest)
@ -491,11 +537,10 @@ function calWcapCalendar_storeItem(bAddItem, item, oldItem, request, netRespFunc
params += "&fetch=1&relativealarm=1&compressed=1&recurring=1";
params += "&emailorcalid=1&fmt-out=text%2Fcalendar";
this.issueNetworkRequest(
request, netRespFunc,
stringToIcal, bIsEvent ? "storeevents" : "storetodos", params,
calIWcapCalendar.AC_COMP_READ |
calIWcapCalendar.AC_COMP_WRITE);
this.issueNetworkRequest(request, netRespFunc, stringToIcal,
bIsEvent ? "storeevents" : "storetodos", params,
calIWcapCalendar.AC_COMP_READ |
calIWcapCalendar.AC_COMP_WRITE);
}
};
@ -505,15 +550,30 @@ function calWcapCalendar_tunnelXProps(destItem, srcItem)
// xxx todo: temp workaround for bug in calItemBase.js
if (!isParent(srcItem))
return;
// tunnel alarm X-MOZ-SNOOZE only if alarm is still set:
var alarmOffset = destItem.alarmOffset;
var enumerator = srcItem.propertyEnumerator;
while (enumerator.hasMoreElements()) {
var prop = enumerator.getNext().QueryInterface(
Components.interfaces.nsIProperty);
var name = prop.name;
if (name.indexOf("X-MOZ-") == 0) {
if (LOG_LEVEL > 1)
log("tunneling " + name, this);
destItem.setProperty(name, prop.value);
try {
var prop = enumerator.getNext().QueryInterface(Components.interfaces.nsIProperty);
var name = prop.name;
if (name.indexOf("X-MOZ-") == 0) {
switch (name) {
// keep snooze stamps for occurrences only and if alarm is still set:
case "X-MOZ-SNOOZE-TIME":
if (!alarmOffset)
break; // alarm has been reset
// fallthru intended:
default:
if (LOG_LEVEL > 1)
log("tunneling " + name + "=" + prop.value, this);
destItem.setProperty(name, prop.value);
break;
}
}
}
catch (exc) {
logError(exc, this);
}
}
};
@ -525,11 +585,11 @@ function calWcapCalendar_adoptItem(item, listener)
var request = new calWcapRequest(
function adoptItem_resp(request, err, newItem) {
if (listener) {
listener.onOperationComplete(
this_.superCalendar, getResultCode(err),
calIOperationListener.ADD,
err ? item.id : newItem.id,
err ? err : newItem);
listener.onOperationComplete(this_.superCalendar,
getResultCode(err),
calIOperationListener.ADD,
err ? item.id : newItem.id,
err ? err : newItem);
}
if (err)
this_.notifyError(err);
@ -554,10 +614,8 @@ function calWcapCalendar_adoptItem(item, listener)
0, null, null, true /* bLeaveMutable */);
if (items.length < 1)
throw new Components.Exception("empty VCALENDAR returned!");
if (items.length > 1) {
this_.notifyError("unexpected number of items: " +
items.length);
}
if (items.length > 1)
this_.notifyError("unexpected number of items: " + items.length);
var newItem = items[0];
this_.tunnelXProps(newItem, item);
item.makeImmutable();
@ -616,10 +674,8 @@ function calWcapCalendar_modifyItem(newItem, oldItem, listener)
0, null, null, true /* bLeaveMutable */);
if (items.length < 1)
throw new Components.Exception("empty VCALENDAR returned!");
if (items.length > 1) {
this_.notifyError("unexpected number of items: " +
items.length);
}
if (items.length > 1)
this_.notifyError("unexpected number of items: " + items.length);
var item = items[0];
this_.tunnelXProps(item, newItem);
item.makeImmutable();
@ -685,7 +741,7 @@ function calWcapCalendar_deleteItem(item, listener)
};
calWcapCalendar.prototype.parseItems = function calWcapCalendar_parseItems(
icalRootComp, itemFilter, maxResult, rangeStart, rangeEnd, bLeaveMutable)
icalRootComp, itemFilter, maxResults, rangeStart, rangeEnd, bLeaveMutable)
{
var items = [];
var unexpandedItems = [];
@ -749,32 +805,10 @@ calWcapCalendar.prototype.parseItems = function calWcapCalendar_parseItems(
}
break;
}
// if (item &&
// item.alarmOffset && !item.entryDate && !item.dueDate) {
// // xxx todo: loss on roundtrip
// log( "app currently does not support " +
// "absolute alarm trigger datetimes. " +
// "Removing alarm from item: " + item.title, this_);
if (item) { // xxx todo: todo alarms currently off
item.alarmOffset = null;
item.alarmLastAck = null;
}
break;
}
}
if (item) {
// var contactsProp = subComp.getFirstProperty("CONTACT");
// if (contactsProp) { // stamp[:lastack]
// var ar = contactsProp.value.split(":");
// if (ar.length > 1) {
// var lastAck = ar[1];
// if (lastAck.length > 0) { // shift to alarm comp:
// item.alarmLastAck = getDatetimeFromIcalString(
// lastAck); // TZID is UTC
// }
// }
// }
if (!item.title) {
// assumed to look at a subscribed calendar,
// so patch title for private items:
@ -812,7 +846,7 @@ calWcapCalendar.prototype.parseItems = function calWcapCalendar_parseItems(
unexpandedItems.push(item);
uid2parent[item.id] = item;
}
else if (maxResult == 0 || items.length < maxResult) {
else if (maxResults == 0 || items.length < maxResults) {
if (LOG_LEVEL > 2) {
log("item: " + item.title + "\n" + item.icalString,
this_);
@ -823,15 +857,15 @@ calWcapCalendar.prototype.parseItems = function calWcapCalendar_parseItems(
}
}
},
maxResult);
maxResults);
// tag "exceptions", i.e. items with rid:
for each ( var item in excItems ) {
for each (var item in excItems) {
var parent = uid2parent[item.id];
if (parent) {
item.parentItem = parent;
item.makeImmutable();
parent.recurrenceInfo.modifyException( item );
parent.recurrenceInfo.modifyException(item);
}
else {
logError("parseItems(): no parent item for " + item.title +
@ -849,13 +883,13 @@ calWcapCalendar.prototype.parseItems = function calWcapCalendar_parseItems(
if (itemFilter & calICalendar.ITEM_FILTER_CLASS_OCCURRENCES) {
for each ( var item in unexpandedItems ) {
if (maxResult != 0 && items.length >= maxResult)
if (maxResults != 0 && items.length >= maxResults)
break;
if (!bLeaveMutable)
item.makeImmutable();
var occurrences = item.recurrenceInfo.getOccurrences(
rangeStart, rangeEnd,
maxResult == 0 ? 0 : maxResult - items.length,
maxResults == 0 ? 0 : maxResults - items.length,
{} );
if (LOG_LEVEL > 1) {
log("item: " + item.title + " has " +
@ -871,9 +905,9 @@ calWcapCalendar.prototype.parseItems = function calWcapCalendar_parseItems(
}
}
else {
if (maxResult != 0 &&
(items.length + unexpandedItems.length) > maxResult) {
unexpandedItems.length = (maxResult - items.length);
if (maxResults != 0 &&
(items.length + unexpandedItems.length) > maxResults) {
unexpandedItems.length = (maxResults - items.length);
}
if (!bLeaveMutable) {
for each ( var item in unexpandedItems ) {
@ -920,12 +954,12 @@ calWcapCalendar.prototype.parseItems = function calWcapCalendar_parseItems(
// item = items[0];
// if (listener) {
// listener.onGetResult(
// this_.superCalendar, Components.results.NS_OK,
// Components.interfaces.calIItemBase,
// this_.superCalendar, NS_OK,
// calIItemBase,
// log("getItem(): success.", this_),
// items.length, items );
// listener.onOperationComplete(
// this_.superCalendar, Components.results.NS_OK,
// this_.superCalendar, NS_OK,
// calIOperationListener.GET,
// items.length == 1 ? items[0].id : null, null );
// this_.log( "item delivered." );
@ -998,7 +1032,7 @@ function getItemFilterParams(itemFilter)
}
calWcapCalendar.prototype.getItems =
function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, listener)
function calWcapCalendar_getItems(itemFilter, maxResults, rangeStart, rangeEnd, listener)
{
// assure DATE-TIMEs:
if (rangeStart && rangeStart.isDate) {
@ -1023,9 +1057,7 @@ function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, l
calIOperationListener.GET,
null, err);
}
if (getResultCode(err) != calIWcapErrors.WCAP_LOGIN_FAILED) {
this_.notifyError(err);
}
this_.notifyError(err, request.suppressOnError);
}
else {
log("getItems(): success.", this_);
@ -1038,10 +1070,13 @@ function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, l
}
},
log("getItems():\n\titemFilter=0x" + itemFilter.toString(0x10) +
",\n\tmaxResult=" + maxResult +
",\n\tmaxResults=" + maxResults +
",\n\trangeStart=" + zRangeStart +
",\n\trangeEnd=" + zRangeEnd, this));
if (itemFilter & calIWcapCalendar.ITEM_FILTER_SUPPRESS_ONERROR)
request.suppressOnError = true;
if (this.session.aboutToLogout) { // limiting the amount of network traffic:
log("about to logout, no results.", this);
request.execRespFunc(null, []);
@ -1063,9 +1098,7 @@ function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, l
log("reusing last getItems() cached data.", this);
if (listener) {
listener.onGetResult(
this.superCalendar,
Components.results.NS_OK,
Components.interfaces.calIItemBase,
this.superCalendar, NS_OK, calIItemBase,
"getItems()", entry.results.length, entry.results);
}
request.execRespFunc(null, entry.results);
@ -1079,8 +1112,8 @@ function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, l
"&emailorcalid=1&fmt-out=text%2Fcalendar");
// setting component-type, compstate filters:
params += getItemFilterParams(itemFilter);
if (maxResult > 0)
params += ("&maxResult=" + maxResult);
if (maxResults > 0)
params += ("&maxResults=" + maxResults);
params += ("&dtstart=" + zRangeStart);
params += ("&dtend=" + zRangeEnd);
@ -1102,10 +1135,10 @@ function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, l
if (!request.succeeded)
throw request.status;
var items = [];
for each ( var period in result ) {
for each (var period in result) {
var item = new CalEvent();
item.id = (g_busyPhantomItemUuidPrefix +
period.start.icalString);
getIcalUTC(period.start));
item.calendar = this_.superCalendar;
item.title = g_busyItemTitle;
item.startDate = period.start;
@ -1114,9 +1147,7 @@ function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, l
items.push(item);
}
listener.onGetResult(
this_.superCalendar,
Components.results.NS_OK,
Components.interfaces.calIItemBase,
this_.superCalendar, NS_OK, calIItemBase,
"getItems()/free-busy", items.length, items);
}
};
@ -1131,7 +1162,7 @@ function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, l
}
else if (listener) {
var items = this_.parseItems(
icalRootComp, itemFilter, maxResult,
icalRootComp, itemFilter, maxResults,
rangeStart, rangeEnd);
if (CACHE_LAST_RESULTS > 0) {
@ -1183,15 +1214,14 @@ function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, l
this_.m_cachedResults.length = CACHE_LAST_RESULTS;
}
listener.onGetResult(
this_.superCalendar,
Components.results.NS_OK,
Components.interfaces.calIItemBase,
"getItems()", items.length, items);
listener.onGetResult(this_.superCalendar, NS_OK, calIItemBase,
"getItems()", items.length, items);
}
},
stringToIcal, "fetchcomponents_by_range", params,
calIWcapCalendar.AC_COMP_READ);
stringToIcal,
(itemFilter & calIWcapCalendar.ITEM_FILTER_BY_ALARM_RANGE)
? "fetchcomponents_by_alarmrange" : "fetchcomponents_by_range",
params, calIWcapCalendar.AC_COMP_READ);
}
catch (exc) {
request.execRespFunc(exc);
@ -1220,7 +1250,7 @@ function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, l
// function calWcapSyncOperationListener_onOperationComplete(
// calendar, status, opType, id, detail)
// {
// if (status != Components.results.NS_OK) {
// if (status != NS_OK) {
// this.
// this.m_syncState.abort( detail );
// }
@ -1260,6 +1290,10 @@ function calWcapCalendar_getItems(itemFilter, maxResult, rangeStart, rangeEnd, l
calWcapCalendar.prototype.syncChangesTo =
function calWcapCalendar_syncChangesTo(destCal, itemFilter, dtFrom_, listener)
{
// xxx todo: move to Thomas
// do NOT puke up error box every three minutes!
itemFilter |= calIWcapCalendar.ITEM_FILTER_SUPPRESS_ONERROR;
var now = getTime(); // new stamp for this sync
var this_ = this;
var request_ = new calWcapRequest(
@ -1271,15 +1305,13 @@ function calWcapCalendar_syncChangesTo(destCal, itemFilter, dtFrom_, listener)
this_.superCalendar, getResultCode(err),
calIWcapCalendar.SYNC, null, err);
}
if (getResultCode(err) != calIWcapErrors.WCAP_LOGIN_FAILED) {
this_.notifyError(err);
}
this_.notifyError(err, request.suppressOnError);
}
else {
log("SYNC succeeded.", this_);
if (listener) {
listener.onOperationComplete(
this_.superCalendar, Components.results.NS_OK,
this_.superCalendar, NS_OK,
calIWcapCalendar.SYNC, null, now);
}
}
@ -1287,15 +1319,10 @@ function calWcapCalendar_syncChangesTo(destCal, itemFilter, dtFrom_, listener)
log("syncChangesTo():\n\titemFilter=0x" + itemFilter.toString(0x10) +
"\n\tdtFrom_=" + getIcalUTC(dtFrom_), this));
if (itemFilter & calIWcapCalendar.ITEM_FILTER_SUPPRESS_ONERROR)
request_.suppressOnError = true;
try {
// xxx todo: better thomas handles this...
// do NOT puke up error box every three minutes!
// again in a few minutes...
if (!this.session.isLoggedIn) {
throw new Components.Exception("Login failed. Invalid session ID.",
calIWcapErrors.WCAP_LOGIN_FAILED);
}
var dtFrom = dtFrom_;
if (dtFrom) {
dtFrom = dtFrom.clone();

Просмотреть файл

@ -37,26 +37,18 @@
*
* ***** END LICENSE BLOCK ***** */
var g_ioService = null;
function getIoService()
{
if (!g_ioService) {
g_ioService = Components.classes["@mozilla.org/network/io-service;1"]
.getService(Components.interfaces.nsIIOService);
}
return g_ioService;
}
//
// init code for globals, prefs:
//
// constants:
const NS_OK = Components.results.NS_OK;
const nsIException = Components.interfaces.nsIException;
const calIWcapSession = Components.interfaces.calIWcapSession;
const calIWcapCalendar = Components.interfaces.calIWcapCalendar;
const calIWcapErrors = Components.interfaces.calIWcapErrors;
const calICalendar = Components.interfaces.calICalendar;
const calIItemBase = Components.interfaces.calIItemBase;
const calIOperationListener = Components.interfaces.calIOperationListener;
// ctors:
@ -87,8 +79,17 @@ var CACHE_LAST_RESULTS_INVALIDATE = 120;
// logging:
var LOG_LEVEL = 0;
// whether alarms are by default turned on/off:
var SUPPRESS_ALARMS = true;
// whether alarms are turned on/off:
var SUPPRESS_ALARMS = false;
var g_ioService = null;
function getIoService() {
if (!g_ioService) {
g_ioService = Components.classes["@mozilla.org/network/io-service;1"]
.getService(Components.interfaces.nsIIOService);
}
return g_ioService;
}
function initWcapProvider()
{
@ -123,12 +124,9 @@ function initWcapProvider()
initLogging();
// some string resources:
g_privateItemTitle = getWcapBundle().GetStringFromName(
"privateItem.title.text");
g_confidentialItemTitle = getWcapBundle().GetStringFromName(
"confidentialItem.title.text");
g_busyItemTitle = getWcapBundle().GetStringFromName(
"busyItem.title.text");
g_privateItemTitle = getWcapBundle().GetStringFromName("privateItem.title.text");
g_confidentialItemTitle = getWcapBundle().GetStringFromName("confidentialItem.title.text");
g_busyItemTitle = getWcapBundle().GetStringFromName("busyItem.title.text");
g_busyPhantomItemUuidPrefix = ("PHANTOM_uuid" + getTime().icalString);
SUPPRESS_ALARMS = getPref("calendar.wcap.suppress_alarms", true);
@ -150,14 +148,13 @@ function initWcapProvider()
var dirService = Components.classes["@mozilla.org/file/directory_service;1"]
.getService(Components.interfaces.nsIProperties);
cacheDir = dirService.get("ProfD", Components.interfaces.nsILocalFile);
cacheDir.append( "wcap" );
cacheDir.append("wcap");
}
CACHE_DIR = cacheDir;
log(CACHE_DIR.path, "cache dir");
if (!CACHE_DIR.exists()) {
CACHE_DIR.create(
Components.interfaces.nsIFile.DIRECTORY_TYPE,
0700 /* read, write, execute/search by owner */ );
CACHE_DIR.create(Components.interfaces.nsIFile.DIRECTORY_TYPE,
0700 /* read, write, execute/search by owner */);
}
}
}

Просмотреть файл

@ -65,7 +65,7 @@ function getErrorModule(rc) {
const NS_ERROR_OFFLINE = generateNetFailure(16);
// The async request completed successfully.
const NS_BINDING_SUCCEEDED = Components.results.NS_OK;
const NS_BINDING_SUCCEEDED = NS_OK;
const NS_BINDING_FAILED = generateNetFailure(1);
const NS_BINDING_ABORTED = generateNetFailure(2);
@ -136,8 +136,8 @@ function netErrorToString( rc )
//
const g_wcapErrorCodes = [
/* -1 */ Components.results.NS_OK, "Logout successful.",
/* 0 */ Components.results.NS_OK, "Command successful.",
/* -1 */ NS_OK, "Logout successful.",
/* 0 */ NS_OK, "Command successful.",
/* 1 */ calIWcapErrors.WCAP_LOGIN_FAILED, "Login failed. Invalid session ID.",
/* 2 */ calIWcapErrors.WCAP_LOGIN_OK_DEFAULT_CALENDAR_NOT_FOUND, "login.wcap was successful, but the default calendar for this user was not found. A new default calendar set to the userid was created.",
/* 3 */ Components.results.NS_ERROR_INVALID_ARG, "No WCAP error code.",
@ -338,7 +338,7 @@ function checkWcapIcalErrno(icalRootComp, expectedErrno) {
function getResultCode(err)
{
if (err === undefined || err === null)
return Components.results.NS_OK;
return NS_OK;
if (isNaN(err)) {
if (err instanceof nsIException)
return err.result;
@ -364,7 +364,7 @@ function errorToString(err)
switch (err) {
case undefined:
case null:
case Components.results.NS_OK:
case NS_OK:
return "NS_OK";
case Components.results.NS_ERROR_INVALID_ARG:
return "NS_ERROR_INVALID_ARG";

Просмотреть файл

@ -65,7 +65,7 @@ function calWcapRequest(respFunc, logContext) {
this.m_logContext = logContext;
this.m_id = generateRequestId();
this.m_isPending = true;
this.m_status = Components.results.NS_OK;
this.m_status = NS_OK;
this.m_respFunc = respFunc;
this.m_attachedRequests = [];
}
@ -74,7 +74,7 @@ calWcapRequest.prototype = {
m_parentRequest: null,
m_id: 0,
m_isPending: true,
m_status: Components.results.NS_OK,
m_status: NS_OK,
m_respFunc: null,
m_attachedRequests: null,
m_locked: false,
@ -84,7 +84,7 @@ calWcapRequest.prototype = {
if (this.parentRequest)
logError("already has parent!", this);
this.detachFromParent(); // detach without error
this.m_parentRequest = req;
return (this.m_parentRequest = req);
},
/** The following locking is necessary when scheduling multiple async
@ -199,12 +199,10 @@ calWcapRequest.prototype = {
return this.m_isPending;
},
get succeeded() {
return (!this.isPending &&
getResultCode(this.status) == Components.results.NS_OK);
return (!this.isPending && Components.isSuccessCode( getResultCode(this.status) ));
},
get status() {
return (this.m_status === null ? Components.results.NS_OK
: this.m_status);
return (this.m_status === null ? NS_OK : this.m_status);
},
cancel: function calWcapRequest_cancel(status)
@ -256,7 +254,7 @@ calWcapNetworkRequest.prototype = {
if (this.parentRequest)
logError("already has parent!", this);
this.detachFromParent(); // detach without error
this.m_parentRequest = req;
return (this.m_parentRequest = req);
},
get id() {

Просмотреть файл

@ -102,31 +102,53 @@ calWcapSession.prototype = {
}
return str;
},
notifyError: function calWcapSession_notifyError(err)
notifyError: function calWcapSession_notifyError(err, suppressOnError)
{
debugger;
var msg = logError(err, this);
this.notifyObservers(
"onError",
err instanceof Components.interfaces.nsIException
? [err.result, err.message] : [isNaN(err) ? -1 : err, msg] );
if (!suppressOnError) {
this.notifyObservers(
"onError",
err instanceof Components.interfaces.nsIException
? [err.result, err.message] : [isNaN(err) ? -1 : err, msg]);
}
},
m_lastOnErrorTime: 0,
m_lastOnErrorNo: 0,
m_lastOnErrorMsg: null,
m_observers: null,
notifyObservers: function calWcapSession_notifyObservers(func, args)
{
if (!g_bShutdown) {
this.m_observers.forEach(
function notifyFunc(obj) {
try {
obj[func].apply(obj, args);
}
catch (exc) {
// don't call notifyError() here:
Components.utils.reportError(exc);
}
});
if (g_bShutdown)
return;
// xxx todo: hack
// suppress identical error bursts when multiple similar calls eg on getItems() fail.
if (func == "onError") {
var now = (new Date()).getTime();
if ((now - this.m_lastOnError) < 2000 &&
(args[0] == this.m_lastOnErrorNo) &&
(args[1] == this.m_lastOnErrorMsg)) {
log("suppressing calIObserver::onError.", this);
return;
}
this.m_lastOnError = now;
this.m_lastOnErrorNo = args[0];
this.m_lastOnErrorMsg = args[1];
}
this.m_observers.forEach(
function notifyFunc(obj) {
try {
obj[func].apply(obj, args);
}
catch (exc) {
// don't call notifyError() here:
Components.utils.reportError(exc);
}
});
},
addObserver: function calWcapSession_addObserver(observer)
@ -187,7 +209,11 @@ calWcapSession.prototype = {
", length: " + this.m_loginQueue.length, this);
if (this.m_loginLock) {
this.m_loginQueue.push(respFunc);
var entry = {
request: request,
respFunc: respFunc
};
this.m_loginQueue.push(entry);
log("login queue: " + this.m_loginQueue.length);
}
else {
@ -210,10 +236,7 @@ calWcapSession.prototype = {
function getSessionId_resp(err, sessionId) {
log("getSessionId_resp(): " + sessionId, this_);
if (err) {
if (getResultCode(err) == calIWcapErrors.WCAP_LOGIN_FAILED) {
// notify login failures once here only:
this_.notifyError(err);
}
this_.notifyError(err, request.suppressOnError);
}
else {
this_.m_sessionId = sessionId;
@ -224,11 +247,15 @@ calWcapSession.prototype = {
this_.m_loginQueue = [];
log("unlocked login queue.", this_);
// first request:
respFunc(err, sessionId);
// dequeue remaining:
if (request.isPending) {
// answere first request:
respFunc(err, sessionId);
}
// and any remaining:
while (queue.length > 0) {
queue.shift()(err, sessionId);
var entry = queue.shift();
if (entry.request.isPending)
entry.respFunc(err, sessionId);
}
});
}
@ -302,8 +329,9 @@ calWcapSession.prototype = {
if (prompt.promptUsernameAndPassword(
getWcapBundle().GetStringFromName("loginDialog.label"),
loginText, outUser, outPW,
getWcapBundle().GetStringFromName("loginDialog.check.text"),
outSavePW)) {
getPref("signon.rememberSignons", true)
? getWcapBundle().GetStringFromName("loginDialog.check.text")
: null, outSavePW)) {
this_.login(request, promptAndLoginLoop_resp,
outUser.value, outPW.value);
}
@ -320,13 +348,12 @@ calWcapSession.prototype = {
if (outSavePW.value) {
// so try to remove old pw from db first:
try {
passwordManager.removeUser(
pwHost, outUser.value);
passwordManager.removeUser(pwHost, outUser.value);
log("removed from pw db: " + pwHost, this_);
}
catch (exc) {
}
try { // save pw under session uri:
try { // to save pw under session uri:
passwordManager.addUser(pwHost, outUser.value, outPW.value);
log("added to pw db: " + pwHost, this_);
}
@ -336,12 +363,11 @@ calWcapSession.prototype = {
}
this_.credentials.userId = outUser.value;
this_.credentials.pw = outPW.value;
this_.setupSession(
sessionId,
request,
function setupSession_resp(err) {
respFunc(err, sessionId);
});
this_.setupSession(sessionId,
request,
function setupSession_resp(err) {
respFunc(err, sessionId);
});
}
}
@ -554,8 +580,8 @@ calWcapSession.prototype = {
this_.defaultCalendar.m_calProps = data;
log("installed default cal props.", this_);
},
stringToXml, "get_calprops",
"&fmt-out=text%2Fxml&calid=" +
stringToXml, "search_calprops",
"&fmt-out=text%2Fxml&searchOpts=3&calid=1&search-string=" +
encodeURIComponent(this_.defaultCalId),
sessionId);
if (getPref("calendar.wcap.subscriptions", false))
@ -634,65 +660,61 @@ calWcapSession.prototype = {
// user may have dangling users referred in his subscription list, so
// retrieve each by each, don't break:
var list = this.getUserPreferences("X-NSCP-WCAP-PREF-icsSubscribed");
for each( var item in list ) {
var calIds = {};
for each (var item in list) {
var ar = item.split(',');
// ',', '$' are not encoded. ',' can be handled here. WTF.
for each ( var a in ar ) {
for each (var a in ar) {
var dollar = a.indexOf('$');
if (dollar >= 0) {
var calId = a.substring(0, dollar);
if (calId == this.defaultCalId)
continue;
try {
var key = encodeURIComponent(calId);
var cal = this_.m_subscribedCals[key];
if (!cal) {
this.issueNetworkRequest_(
request,
function calprops_resp(err, xml) {
try {
if (err)
throw err;
var cal = createWcapCalendar(this_, xml);
this_.m_subscribedCals[encodeURIComponent(cal.calId)] = cal;
getCalendarManager().registerCalendar(cal);
log("installed subscribed calendar: " + cal.calId, this_);
}
catch (exc) {
// ignore but log any errors on subscribed calendars:
logError(exc, this_);
}
},
stringToXml, "get_calprops",
"&fmt-out=text%2Fxml&calid=" + key,
sessionId);
// var listener = {
// onRequestResult: function onRequestResult(request, result) {
// try {
// if (!request.succeeded)
// throw request.status;
// if (result.length < 1)
// throw Components.results.NS_ERROR_UNEXPECTED;
// var cal = result[0];
// getCalendarManager().registerCalendar(cal);
// log("installed subscribed calendar: " + cal.calId,
// this_);
// }
// catch (exc) {
// logError(exc, this_);
// }
// }
// };
// this.searchForCalendars(
// calId,
// calIWcapSession.SEARCH_STRING_EXACT |
// calIWcapSession.SEARCH_INCLUDE_CALID,
// listener);
if (calId != this.defaultCalId)
calIds[calId] = true;
}
}
}
var issuedSearchRequests = {};
for (var calId in calIds) {
if (!this_.m_subscribedCals[calId]) {
var listener = {
onRequestResult: function search_onRequestResult(request, result) {
try {
if (!request.succeeded)
throw request.status;
if (result.length < 1)
throw Components.results.NS_ERROR_UNEXPECTED;
for each (var cal in result) {
try {
var calId = cal.calId;
if (calIds[calId] && !this_.m_subscribedCals[calId]) {
this_.m_subscribedCals[calId] = cal;
getCalendarManager().registerCalendar(cal);
log("installed subscribed calendar: " + calId, this_);
}
}
catch (exc) { // ignore but log any errors on subscribed calendars:
logError(exc, this_);
}
}
}
catch (exc) { // ignore but log any errors on subscribed calendars:
logError(exc, this_);
}
}
catch (exc) { // ignore but log any errors on subscribed calendars:
logError(exc, this);
}
};
var colon = calId.indexOf(':');
if (colon >= 0) // searching for secondary calendars doesn't work. WTF.
calId = calId.substring(0, colon);
if (!issuedSearchRequests[calId]) {
issuedSearchRequests[calId] = true;
this.searchForCalendars(
calId,
calIWcapSession.SEARCH_STRING_EXACT |
calIWcapSession.SEARCH_INCLUDE_CALID |
// else searching for secondary calendars doesn't work:
calIWcapSession.SEARCH_INCLUDE_OWNER,
20, listener);
}
}
}
@ -789,6 +811,7 @@ calWcapSession.prototype = {
log("set uri: " + this.uri.spec, this);
}
}
return thatUri;
},
get userId() { return this.credentials.userId; },
@ -837,7 +860,7 @@ calWcapSession.prototype = {
var ret = [];
var ar = this.getUserPreferences("X-NSCP-WCAP-PREF-ceDefaultAlarmEmail");
if (ar.length > 0 && ar[0].length > 0) {
for each ( var i in ar ) {
for each (var i in ar) {
ret = ret.concat( i.split(/[;,]/).map(trimString) );
}
}
@ -846,7 +869,7 @@ calWcapSession.prototype = {
},
searchForCalendars:
function calWcapSession_searchForCalendars(searchString, searchOptions, listener)
function calWcapSession_searchForCalendars(searchString, searchOptions, maxResults, listener)
{
var this_ = this;
var request = new calWcapRequest(
@ -862,6 +885,8 @@ calWcapSession.prototype = {
var params = ("&fmt-out=text%2Fxml&search-string=" +
encodeURIComponent(searchString));
params += ("&searchOpts=" + (searchOptions & 3).toString(10));
if (maxResults > 0)
params += ("&maxResults=" + maxResults);
if (searchOptions & calIWcapSession.SEARCH_INCLUDE_CALID)
params += "&calid=1";
if (searchOptions & calIWcapSession.SEARCH_INCLUDE_NAME)
@ -890,7 +915,7 @@ calWcapSession.prototype = {
var ar = filterXmlNodes("X-NSCP-CALPROPS-RELATIVE-CALID", node);
if (ar.length > 0) {
var calId = ar[0];
var cal = this_.m_subscribedCals[encodeURIComponent(calId)];
var cal = this_.m_subscribedCals[calId];
if (!cal) {
if (calId == this_.defaultCalId)
cal = this_.defaultCalendar;
@ -943,16 +968,16 @@ calWcapSession.prototype = {
var this_ = this;
var request = new calWcapRequest(
function getFreeBusyTimes_resp(request, err, data) {
switch (getResultCode(err)) {
case Components.results.NS_OK:
break;
var rc = getResultCode(err);
switch (rc) {
case calIWcapErrors.WCAP_NO_ERRNO: // workaround
case calIWcapErrors.WCAP_ACCESS_DENIED_TO_CALENDAR:
case calIWcapErrors.WCAP_CALENDAR_DOES_NOT_EXIST:
log("getFreeBusyTimes_resp() error: " + errorToString(err), this_);
break;
default:
this_.notifyError(err);
if (!Components.isSuccessCode(rc))
this_.notifyError(err);
break;
}
if (listener)
@ -1069,14 +1094,12 @@ calWcapSession.prototype = {
cal = null;
}
try {
// make sure the calendar belongs to this session:
if (cal && cal.session.uri.equals(this.uri)) {
if (!cal.isDefaultCalendar) {
var key = encodeURIComponent(cal.calId);
if (!this.m_subscribedCals[key])
this.modifySubscriptions(cal, true/*bSubscibe*/);
this.m_subscribedCals[key] = cal;
}
// make sure the calendar belongs to this session and is a subscription:
if (cal && cal.session.uri.equals(this.uri) && !cal.isDefaultCalendar) {
var calId = cal.calId;
if (!this.m_subscribedCals[calId])
this.modifySubscriptions(cal, true/*bSubscibe*/);
this.m_subscribedCals[calId] = cal;
}
}
catch (exc) { // never break the listener chain
@ -1094,18 +1117,13 @@ calWcapSession.prototype = {
cal = null;
}
try {
// make sure the calendar belongs to this session:
if (cal && cal.session.uri.equals(this.uri)) {
if (cal.isDefaultCalendar) {
// whole account is being removed, so logout before:
this.logout(null);
}
else {
var key = encodeURIComponent(cal.calId);
if (this.m_subscribedCals[key]) {
delete this.m_subscribedCals[key];
this.modifySubscriptions(cal, false/*bSubscibe*/);
}
// don't logout here (even if this is the default calendar): upcoming calls may occur.
// make sure the calendar belongs to this session and is a subscription:
if (cal && cal.session.uri.equals(this.uri) && !cal.isDefaultCalendar) {
var calId = cal.calId;
if (this.m_subscribedCals[calId]) {
delete this.m_subscribedCals[calId];
this.modifySubscriptions(cal, false/*bSubscibe*/);
}
}
}

Просмотреть файл

@ -244,13 +244,12 @@ function isEvent(item) {
function isParent(item) {
if (item.id != item.parentItem.id) {
throw new Components.Exception(
"proxy has different id than its parent!");
throw new Components.Exception("proxy has different id than its parent!");
}
return (!item.recurrenceId);
}
function forEachIcalComponent(icalRootComp, componentType, func, maxResult)
function forEachIcalComponent(icalRootComp, componentType, func, maxResults)
{
var itemCount = 0;
// libical returns the vcalendar component if there is just
@ -260,11 +259,11 @@ function forEachIcalComponent(icalRootComp, componentType, func, maxResult)
for ( var calComp = (icalRootComp.componentType == "VCALENDAR"
? icalRootComp
: icalRootComp.getFirstSubcomponent("VCALENDAR"));
calComp != null && (!maxResult || itemCount < maxResult);
calComp != null && (!maxResults || itemCount < maxResults);
calComp = icalRootComp.getNextSubcomponent("VCALENDAR") )
{
for ( var subComp = calComp.getFirstSubcomponent(componentType);
subComp != null && (!maxResult || itemCount < maxResult);
subComp != null && (!maxResults || itemCount < maxResults);
subComp = calComp.getNextSubcomponent(componentType) )
{
func( subComp );
@ -278,7 +277,7 @@ function filterXmlNodes(name, rootNode)
var ret = [];
if (rootNode) {
var nodeList = rootNode.getElementsByTagName(name);
for ( var i = 0; i < nodeList.length; ++i ) {
for (var i = 0; i < nodeList.length; ++i) {
var node = nodeList.item(i);
ret.push( trimString(node.textContent) );
}
@ -287,7 +286,7 @@ function filterXmlNodes(name, rootNode)
}
function trimString(str) {
return str.replace( /(^\s+|\s+$)/g, "" );
return str.replace(/(^\s+|\s+$)/g, "");
}
function getTime() {

Просмотреть файл

@ -142,6 +142,13 @@ interface calIWcapCalendar : calICalendar
/* xxx todo: limit to currently needed ones: NEEDS-ACTION */
/**
* Scope: getItems only
* Whether getItems should only return items that have alarms set for the
* specified range.
*/
const unsigned long ITEM_FILTER_BY_ALARM_RANGE = 1 << 23;
// /**
// * Scope: Attendee
// * The event or todo is an invitation from another
@ -192,6 +199,7 @@ interface calIWcapCalendar : calICalendar
// */
// const unsigned long ITEM_FILTER_REQUEST_WAITFORREPLY = 1 << 30;
const unsigned long ITEM_FILTER_SUPPRESS_ONERROR = 1 << 31;
/* xxx todo sync feature: separate into own interface? */
/** xxx todo: to be moved to calIOperationListener?

Просмотреть файл

@ -88,16 +88,17 @@ interface calIWcapSession : nsISupports
* Searches for calendars matching the specified searchString.
* Results are notified to the passed listener instance as
* an array of calendar instances.
* The maximum returned count of calendars
* (with respect to Sun calendar servers) is limited to 200.
*
* @param searchString the search string to match
* @param searchOptions the search options
* @param maxResults maximum number of results
* (0 means default, e.g. 200 with respect to Sun calendar servers)
* @param listener listener called with an array of calIWcapCalendar objects
* @return request object to track operation
*/
calIWcapRequest searchForCalendars(in string searchString,
in unsigned long searchOptions,
in unsigned long maxResults,
in calIWcapRequestResultListener listener);
/* xxx todo freebusy: separate into own interface? */