diff --git a/NEWS b/NEWS
index 601d6e8e5..7d0ed35b3 100644
--- a/NEWS
+++ b/NEWS
@@ -6,6 +6,7 @@ Enhancements
- [web] new button to mark a task as completed (#4531)
- [web] new button to reset Calendar categories to defaults
- [web] moved the unseen messages count to the beginning of the window's title (#4553)
+ - [web] allow export of calendars subscriptions (#4560)
Bug fixes
- [web] include mail account name in form validation (#4532)
diff --git a/UI/Scheduler/product.plist b/UI/Scheduler/product.plist
index f03d2ba6f..9212e850f 100644
--- a/UI/Scheduler/product.plist
+++ b/UI/Scheduler/product.plist
@@ -226,7 +226,7 @@
SOGoAppointmentFolderICS = {
methods = {
export = {
- protectedBy = "View";
+ protectedBy = "Access Contents Information";
actionClass = "UIxCalFolderActions";
actionName = "export";
};
diff --git a/UI/Templates/SchedulerUI/UIxCalMainView.wox b/UI/Templates/SchedulerUI/UIxCalMainView.wox
index ea19c3f15..a021111a4 100644
--- a/UI/Templates/SchedulerUI/UIxCalMainView.wox
+++ b/UI/Templates/SchedulerUI/UIxCalMainView.wox
@@ -487,7 +487,7 @@
ng-show="list.component.$isLoading()">
+ md-diameter="32">
@@ -572,7 +572,7 @@
-
+
diff --git a/UI/WebServerResources/js/Scheduler/Calendar.service.js b/UI/WebServerResources/js/Scheduler/Calendar.service.js
index fc5428ecb..5fef35e96 100644
--- a/UI/WebServerResources/js/Scheduler/Calendar.service.js
+++ b/UI/WebServerResources/js/Scheduler/Calendar.service.js
@@ -554,14 +554,26 @@
* @returns a promise of the HTTP operation
*/
Calendar.prototype.export = function() {
- var options;
+ var options, resource, ownerPaths, realOwnerId, path, index;
options = {
type: 'application/octet-stream',
filename: this.name + '.ics'
};
- return Calendar.$$resource.open(this.id + '.ics', 'export', null, options);
+ if (this.isSubscription) {
+ index = this.urls.webDavICSURL.indexOf('/dav/');
+ ownerPaths = this.urls.webDavICSURL.substring(index + 5).split(/\//);
+ realOwnerId = ownerPaths[0];
+ resource = Calendar.$$resource.userResource(realOwnerId);
+ path = ownerPaths.splice(ownerPaths.length - 2).join('/');
+ }
+ else {
+ resource = Calendar.$$resource;
+ path = this.id + '.ics';
+ }
+
+ return resource.open(path, 'export', null, options);
};
/**