From c872fb4d9c68382431a52181073ba1964cf44c22 Mon Sep 17 00:00:00 2001 From: Hivert Quentin Date: Fri, 10 Nov 2023 15:07:14 +0100 Subject: [PATCH 1/8] feat(preferences): can set SOGoForwardConstraints to 3 to accept both internal and external domains from SOGoForwardConstraintsDomains --- Documentation/SOGoInstallationGuide.asciidoc | 10 ++-- SoObjects/SOGo/NSString+Utilities.h | 1 + SoObjects/SOGo/NSString+Utilities.m | 12 ++++ SoObjects/SOGo/SOGoDomainDefaults.m | 2 +- UI/PreferencesUI/UIxPreferences.m | 58 ++++++++++++++++++- .../js/Preferences/PreferencesController.js | 7 +++ 6 files changed, 82 insertions(+), 8 deletions(-) diff --git a/Documentation/SOGoInstallationGuide.asciidoc b/Documentation/SOGoInstallationGuide.asciidoc index 2adf306a3..2db47d228 100644 --- a/Documentation/SOGoInstallationGuide.asciidoc +++ b/Documentation/SOGoInstallationGuide.asciidoc @@ -2280,12 +2280,14 @@ Defaults to `NO` when unset. |D |SOGoForwardConstraints |Parameter used to set constraints on possible addresses used when automatically forwarding mails. When set to `0` (default), no constraint -is enforced. When set to `1`, only internal domains can be used. When -set to `2`, only external domains can be used. +is enforced. When set to `1`, only internal domains can be used. +When set to `2`, only external domains defined in `SOGoForwardConstraintsDomains` +can be used. When set to `3`, internal domains and other domains defined +in `SOGoForwardConstraintsDomains` can be used. |D |SOGoForwardConstraintsDomains -|Parameter used to set which domains are allowed as external domains -when SOGoForwardConstraints is set to `2`. For example, setting: +|Parameter used to set which external domains are allowed +when SOGoForwardConstraints is set to `2` or `3`. For example, setting: SOGoForwardConstraintsDomains = ("gmail.com", "googlemail.com"); diff --git a/SoObjects/SOGo/NSString+Utilities.h b/SoObjects/SOGo/NSString+Utilities.h index cdec73f75..636612dc4 100644 --- a/SoObjects/SOGo/NSString+Utilities.h +++ b/SoObjects/SOGo/NSString+Utilities.h @@ -65,6 +65,7 @@ - (id) objectFromJSONString; /* bare email addresses */ +- (NSString *) mailDomain; - (NSString *) pureEMailAddress; - (NSString *) asQPSubjectString: (NSString *) encoding; diff --git a/SoObjects/SOGo/NSString+Utilities.m b/SoObjects/SOGo/NSString+Utilities.m index cf722d923..06a72a686 100644 --- a/SoObjects/SOGo/NSString+Utilities.m +++ b/SoObjects/SOGo/NSString+Utilities.m @@ -609,6 +609,18 @@ static int cssEscapingCount; return newString; } + +- (NSString *) mailDomain +{ + NSArray *mailSeparated; + + mailSeparated = [self componentsSeparatedByString: @"@"]; + if([mailSeparated count] == 2) + return [mailSeparated objectAtIndex: 1]; + [self logWithFormat: @"Error while extracting domain from : %@", self]; + return nil; +} + - (NSString *) pureEMailAddress { NSString *pureAddress; diff --git a/SoObjects/SOGo/SOGoDomainDefaults.m b/SoObjects/SOGo/SOGoDomainDefaults.m index 86fdd8de7..d508905c7 100644 --- a/SoObjects/SOGo/SOGoDomainDefaults.m +++ b/SoObjects/SOGo/SOGoDomainDefaults.m @@ -217,7 +217,7 @@ v = [self integerForKey: @"SOGoForwardConstraints"]; - return (v > 2 ? 0 : v); + return (v > 3 ? 0 : v); } - (NSArray *) forwardConstraintsDomains diff --git a/UI/PreferencesUI/UIxPreferences.m b/UI/PreferencesUI/UIxPreferences.m index a95515dfb..fcc85137a 100644 --- a/UI/PreferencesUI/UIxPreferences.m +++ b/UI/PreferencesUI/UIxPreferences.m @@ -1532,6 +1532,44 @@ static NSArray *reminderValues = nil; return (forwardEnabled ? @"true" : @"false"); } +- (BOOL) doForwardsMatchTheConstraints: (NSArray *) forwardMails +{ + NSArray *allUserMails, *domainConstraints; + NSMutableArray *allUserDomains; + NSString *currentMail, *currentDomain, *userMail; + SOGoDomainDefaults *dd; + int constraint; + + dd = [[context activeUser] domainDefaults]; + constraint = [dd forwardConstraints]; + + if(constraint > 0) + { + allUserMails = [[user allEmails] uniqueObjects]; + allUserDomains = [NSMutableArray array]; + for(userMail in allUserMails) + { + [allUserDomains push: [userMail mailDomain]]; + } + for(currentMail in forwardMails) + { + currentDomain = [currentMail mailDomain]; + domainConstraints = [dd forwardConstraintsDomains]; + if (constraint == 1 && [allUserDomains indexOfObject: currentDomain] == NSNotFound) + return NO; + else if (constraint == 2 && [allUserDomains indexOfObject: currentDomain] != NSNotFound) + return NO; + else if (constraint == 2 && (!domainConstraints || [domainConstraints indexOfObject: currentDomain] == NSNotFound)) + return NO; + else if (constraint == 3 && + [allUserDomains indexOfObject: currentDomain] == NSNotFound && + (!domainConstraints || [domainConstraints indexOfObject: currentDomain] == NSNotFound)) + return NO; + } + } + return YES; +} + /** * @api {post} /so/:username/Preferences/save Save user's defaults and settings * @apiVersion 1.0.0 @@ -1561,8 +1599,8 @@ static NSArray *reminderValues = nil; if ((v = [o objectForKey: @"defaults"])) { NSMutableDictionary *sanitizedLabels; - NSArray *allKeys, *accounts, *identities; - NSDictionary *newLabels; + NSArray *allKeys, *accounts, *identities, *forwardMails; + NSDictionary *newLabels, *forwardPref; NSString *name; id loginModule; @@ -1600,6 +1638,20 @@ static NSArray *reminderValues = nil; [v removeObjectForKey: @"SOGoAlternateAvatar"]; [[[user userDefaults] source] removeObjectForKey: @"SOGoAlternateAvatar"]; } + + //We check if there are forward constraints + forwardPref = [v objectForKey: @"Forward"]; + if(forwardPref && [forwardPref isKindOfClass: [NSDictionary class]] + && [forwardPref objectForKey: @"enabled"] + && [[forwardPref objectForKey: @"enabled"] boolValue]) + { + BOOL doForward = NO; + forwardMails = [forwardPref objectForKey: @"forwardAddress"]; + if (forwardMails && [forwardMails isKindOfClass: [NSArray class]] && [forwardMails count]>0) + doForward = [self doForwardsMatchTheConstraints: [forwardPref objectForKey: @"forwardAddress"]]; + if(!doForward) + [v removeObjectForKey: @"Forward"]; + } if ([self userHasMailAccess]) { @@ -1658,7 +1710,7 @@ static NSArray *reminderValues = nil; // - forceDefaultIdentity => SOGoMailForceDefaultIdentity // - receipts.receiptAction => SOGoMailReceiptAllow // - receipts.receiptNonRecipientAction => SOGoMailReceiptNonRecipientAction - // - receipts.receiptOutsideDomainAction => SOGoMailReceiptOutsideDomainAction + // - receipts.receiptOutsideDomaforwardAddressinAction => SOGoMailReceiptOutsideDomainAction // - receipts.receiptAnyAction => SOGoMailReceiptAnyAction // - security.alwaysSign => SOGoMailCertificateAlwaysSign // - security.alwaysEncrypt => SOGoMailCertificateAlwaysEncrypt diff --git a/UI/WebServerResources/js/Preferences/PreferencesController.js b/UI/WebServerResources/js/Preferences/PreferencesController.js index 921e80687..c92537bb1 100644 --- a/UI/WebServerResources/js/Preferences/PreferencesController.js +++ b/UI/WebServerResources/js/Preferences/PreferencesController.js @@ -394,6 +394,13 @@ $window.forwardConstraintsDomains.indexOf(domain) < 0) { throw new Error(l("You are not allowed to forward your messages to this domain:") + " " + domain); } + else if ($window.forwardConstraints == 3 && + domains.indexOf(domain) < 0 && + ($window.forwardConstraintsDomains.length > 0 && + $window.forwardConstraintsDomains.indexOf(domain) < 0)) { + // If constraints mode is 3 and the domain is not an internal nor in forwardConstraintsDomains list, throw an error + throw new Error(l("You are not allowed to forward your messages to this domain:")+ " " + domain); + } } return true; From 605d8b1169233f4b51fc301ee5085951ad6ac558 Mon Sep 17 00:00:00 2001 From: Hivert Quentin Date: Sat, 11 Nov 2023 00:00:50 -0500 Subject: [PATCH 2/8] chore(js/css): update generated files --- UI/WebServerResources/js/Preferences.js | 2 +- UI/WebServerResources/js/Preferences.js.map | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/UI/WebServerResources/js/Preferences.js b/UI/WebServerResources/js/Preferences.js index a28829fbb..b6049eda7 100644 --- a/UI/WebServerResources/js/Preferences.js +++ b/UI/WebServerResources/js/Preferences.js @@ -1,2 +1,2 @@ -!function(){"use strict";function e(e,t){e.state("preferences",{abstract:!0,views:{preferences:{templateUrl:"preferences.html",controller:"PreferencesController",controllerAs:"app"}}}).state("preferences.general",{url:"/general",views:{module:{templateUrl:"generalPreferences.html"}}}).state("preferences.calendars",{url:"/calendars",views:{module:{templateUrl:"calendarsPreferences.html"}}}).state("preferences.addressbooks",{url:"/addressbooks",views:{module:{templateUrl:"addressbooksPreferences.html"}}}).state("preferences.mailer",{url:"/mailer",views:{module:{templateUrl:"mailerPreferences.html"}}}),t.rules.otherwise("/general")}function t(e,t,i,a){e.DebugEnabled||a.defaultErrorHandler(function(){}),i.onError({to:"preferences.**"},function(e){"preferences"==e.to().name||e.ignored()||(t.error("transition error to "+e.to().name+": "+e.error().detail),a.go({state:"preferences"}))})}angular.module("SOGo.PreferencesUI",["ui.router","sgCkeditor","angularFileUpload","SOGo.Common","SOGo.MailerUI","SOGo.ContactsUI","SOGo.Authentication","as.sortable"]).config(e).run(t),e.$inject=["$stateProvider","$urlServiceProvider"],t.$inject=["$window","$log","$transitions","$state"]}(),function(){"use strict";function e(s,e,t,i,r,a,n,o,c,d,f){var u=this,h=e.usesCASAuthentication||e.usesSAML2Authentication;function m(){u.account.security&&u.account.security.hasCertificate&&u.account.$certificate().then(function(e){u.certificate=e},function(){delete u.account.security.hasCertificate})}function p(e){e=0this.maxSize?r.alert(l("Error"),l("Data too big. Please contact technical support.")):t.hide()}}e.$inject=["$timeout","$window","$mdDialog","FileUploader","Dialog","sgSettings","defaults","account","accountId","mailCustomFromEnabled","maxSize"],angular.module("SOGo.PreferencesUI").controller("AccountDialogController",e)}(),function(){"use strict";function e(e,t,i,a,s,r,n,o,c){var d=t.sieveCapabilities,f=t.forwardEnabled,u=t.notificationEnabled;t.vacationEnabled;this.filter=s,this.mailboxes=r,this.labels=n,this.fieldLabels={subject:l("Subject"),from:l("From"),to:l("To"),cc:l("Cc"),to_or_cc:l("To or Cc"),size:l("Size (Kb)"),header:l("Header")},-1e.endDate.getTime()&&(e.startDate=new Date(e.endDate.getTime()),e.startDate.addDays(-1))},this.toggleVacationEndDate=function(){var e=this.preferences.defaults.Vacation;e.endDateEnabled&&(e.endDate||(e.endDate=new Date),e.startDateEnabled)&&e.startDate&&e.endDate.getTime()=t.Vacation.startDate.getTime():i},this.toggleVacationStartTime=function(){var e=this.preferences.defaults.Vacation;e.startTimeEnabled&&!e.startTime&&(e.startTime=new Date)},this.toggleVacationEndTime=function(){var e=this.preferences.defaults.Vacation;e.endTimeEnabled&&!e.endTime&&(e.endTime=new Date)},this.contactFilter=function(e){return p.$filterAll(e,[],{priority:"gcs"}).then(function(e){var t=[];return _.forEach(_.invokeMap(e,"explode"),function(e){_.forEach(e,function(e){t.push(e)})}),_.uniqBy(t,function(e){return e.$$fullname+" "+e.$$email+" "+e.containername})})},this.ignoreReturn=function(e){if(13==e.keyCode)return e.stopPropagation(),e.preventDefault(),!1;186==e.keyCode&&"ü"==e.key&&(e.stopPropagation(),e.preventDefault(),(e=r.document.getElementById(e.target.id)).value=e.value+"ü")},this.addRecipient=function(e,t){var i,a,s,r,n=this.autocomplete[t];if(angular.isString(e)){for(r="",s=0;sthis.maxSize?r.alert(l("Error"),l("Data too big. Please contact technical support.")):t.hide()}}e.$inject=["$timeout","$window","$mdDialog","FileUploader","Dialog","sgSettings","defaults","account","accountId","mailCustomFromEnabled","maxSize"],angular.module("SOGo.PreferencesUI").controller("AccountDialogController",e)}(),function(){"use strict";function e(e,t,i,a,s,r,n,o,c){var d=t.sieveCapabilities,f=t.forwardEnabled,u=t.notificationEnabled;t.vacationEnabled;this.filter=s,this.mailboxes=r,this.labels=n,this.fieldLabels={subject:l("Subject"),from:l("From"),to:l("To"),cc:l("Cc"),to_or_cc:l("To or Cc"),size:l("Size (Kb)"),header:l("Header")},-1e.endDate.getTime()&&(e.startDate=new Date(e.endDate.getTime()),e.startDate.addDays(-1))},this.toggleVacationEndDate=function(){var e=this.preferences.defaults.Vacation;e.endDateEnabled&&(e.endDate||(e.endDate=new Date),e.startDateEnabled)&&e.startDate&&e.endDate.getTime()=t.Vacation.startDate.getTime():i},this.toggleVacationStartTime=function(){var e=this.preferences.defaults.Vacation;e.startTimeEnabled&&!e.startTime&&(e.startTime=new Date)},this.toggleVacationEndTime=function(){var e=this.preferences.defaults.Vacation;e.endTimeEnabled&&!e.endTime&&(e.endTime=new Date)},this.contactFilter=function(e){return p.$filterAll(e,[],{priority:"gcs"}).then(function(e){var t=[];return _.forEach(_.invokeMap(e,"explode"),function(e){_.forEach(e,function(e){t.push(e)})}),_.uniqBy(t,function(e){return e.$$fullname+" "+e.$$email+" "+e.containername})})},this.ignoreReturn=function(e){if(13==e.keyCode)return e.stopPropagation(),e.preventDefault(),!1;186==e.keyCode&&"ü"==e.key&&(e.stopPropagation(),e.preventDefault(),(e=r.document.getElementById(e.target.id)).value=e.value+"ü")},this.addRecipient=function(e,t){var i,a,s,r,n=this.autocomplete[t];if(angular.isString(e)){for(r="",s=0;s Date: Mon, 13 Nov 2023 23:02:07 +0100 Subject: [PATCH 3/8] fix(core): Fix calendar issues with Thunderbird related to vlist exclusion. Fix error log on photo. Closes #5885 --- SoObjects/Contacts/NGVCard+SOGo.m | 2 +- SoObjects/SOGo/SOGoGCSFolder.m | 6 ++++-- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/SoObjects/Contacts/NGVCard+SOGo.m b/SoObjects/Contacts/NGVCard+SOGo.m index d5b5ed8c2..d1be8dccd 100644 --- a/SoObjects/Contacts/NGVCard+SOGo.m +++ b/SoObjects/Contacts/NGVCard+SOGo.m @@ -418,7 +418,7 @@ convention: [self setCategories: [o componentsSeparatedByString: @","]]; // Photo - if ([ldifRecord objectForKey: @"photo"]) + if ([ldifRecord objectForKey: @"photo"] && [ldifRecord objectForKey: @"photo"] != [NSNull null]) [self setPhoto: [[ldifRecord objectForKey: @"photo"] stringByEncodingBase64]]; [self cleanupEmptyChildren]; diff --git a/SoObjects/SOGo/SOGoGCSFolder.m b/SoObjects/SOGo/SOGoGCSFolder.m index 9ff8db637..58a958de8 100644 --- a/SoObjects/SOGo/SOGoGCSFolder.m +++ b/SoObjects/SOGo/SOGoGCSFolder.m @@ -739,7 +739,8 @@ static NSArray *childRecordFields = nil; qualifier = aclQualifier; // For Thunderbird, disable contact list - if ([[context request] isThunderbird]) { + // This will be removed when VCARD will be implemented + if ([[context request] isThunderbird] && [self isKindOfClass: NSClassFromString(@"SOGoContactGCSFolder")]) { vlistExclusionQualifier = [EOQualifier qualifierWithQualifierFormat: @"c_component != 'vlist'"]; qualifier = [[[EOAndQualifier alloc] initWithQualifiers: vlistExclusionQualifier, @@ -1191,7 +1192,8 @@ static NSArray *childRecordFields = nil; folder = [self ocsFolder]; // For Thunderbird, disable contact list - if ([[context request] isThunderbird]) { + // This will be removed when VCARD will be implemented + if ([[context request] isThunderbird] && [self isKindOfClass: NSClassFromString(@"SOGoContactGCSFolder")]) { vlistExclusionQualifier = [EOQualifier qualifierWithQualifierFormat: @"c_component != 'vlist'"]; qualifier = [[[EOAndQualifier alloc] initWithQualifiers: vlistExclusionQualifier, From 1e8127b46122e83df02c394536950288b0ee16aa Mon Sep 17 00:00:00 2001 From: Hivert Quentin Date: Thu, 16 Nov 2023 11:18:23 +0100 Subject: [PATCH 4/8] fix(calendar): properly set the start date range for yearly events --- SOPE/NGCards/iCalYearlyRecurrenceCalculator.m | 36 +++++++++++++------ 1 file changed, 25 insertions(+), 11 deletions(-) diff --git a/SOPE/NGCards/iCalYearlyRecurrenceCalculator.m b/SOPE/NGCards/iCalYearlyRecurrenceCalculator.m index 5c1569c61..5e4fadc6f 100644 --- a/SOPE/NGCards/iCalYearlyRecurrenceCalculator.m +++ b/SOPE/NGCards/iCalYearlyRecurrenceCalculator.m @@ -44,10 +44,11 @@ { NSMutableArray *ranges; NSArray *byMonth; - NSCalendarDate *firStart, *lastDate, *rStart, *rEnd, *until, *referenceDate; + NSCalendarDate *firStart, *lastDate, *rStart, *rEnd, *until, *referenceDate, *rTemp; + NSInteger *hoursOfOffset; iCalMonthlyRecurrenceCalculator *monthlyCalc; unsigned j, yearIdxInRange, numberOfYearsInRange, count, interval, monthDiff; - int diff, repeatCount, currentMonth; + int diff, repeatCount, currentMonth, origNbDaysInMonth; firStart = [firstRange startDate]; rStart = [_r startDate]; @@ -186,18 +187,31 @@ days: 0]; - //Due to the bug with dateByAddingYears, we have to take off one day (see line 133) - rStart = [NSCalendarDate dateWithYear: [rStart yearOfCommonEra] - month: [rStart monthOfYear] - day: 0 - hour: [rStart hourOfDay] - minute: [rStart minuteOfHour] - second: 0 - timeZone: [rStart timeZone]]; + //Due to the bug with dateByAddingYears, we may take the previous day (see line 133) + hoursOfOffset = [rStart hourOfDay]; + origNbDaysInMonth = [rStart numberOfDaysInMonth]; + if(hoursOfOffset > 12) { + //If rStart is 1st 22:00, we should start at the previous day 22:00 + rTemp = [NSCalendarDate dateWithYear: [rStart yearOfCommonEra] + month: 1+([rStart monthOfYear]-2)%12 + day: 1 + hour: [rStart hourOfDay] + minute: [rStart minuteOfHour] + second: 0 + timeZone: [rStart timeZone]]; + rStart = [NSCalendarDate dateWithYear: [rStart yearOfCommonEra] + month: 1+([rStart monthOfYear]-2)%12 + day: [rTemp numberOfDaysInMonth] + hour: [rStart hourOfDay] + minute: [rStart minuteOfHour] + second: 0 + timeZone: [rStart timeZone]]; + } + rEnd = [rStart dateByAddingYears: 0 months: 0 - days: [rStart numberOfDaysInMonth]]; + days: origNbDaysInMonth]; rangeForMonth = [NGCalendarDateRange calendarDateRangeWithStartDate: rStart From 0023a9ce3c4027bb32699efc5529a4a53d7699f6 Mon Sep 17 00:00:00 2001 From: Hivert Quentin Date: Fri, 17 Nov 2023 09:24:12 +0100 Subject: [PATCH 5/8] fix(calendar): do not let DURATION and DTEND be both present in vevent --- SOPE/NGCards/iCalEvent.m | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/SOPE/NGCards/iCalEvent.m b/SOPE/NGCards/iCalEvent.m index 7d39064dc..8e192f438 100644 --- a/SOPE/NGCards/iCalEvent.m +++ b/SOPE/NGCards/iCalEvent.m @@ -72,8 +72,14 @@ - (void) setEndDate: (NSCalendarDate *) newEndDate { + CardElement *c; + [(iCalDateTime *) [self uniqueChildWithTag: @"dtend"] setDateTime: newEndDate]; + + c = [self uniqueChildWithTag: @"duration"]; + if (c) + [self removeChild: c]; } - (NSCalendarDate *) endDate From ca2c5c188ed980629f494e5b8e23ba42cdd54f58 Mon Sep 17 00:00:00 2001 From: smizrahi Date: Fri, 17 Nov 2023 10:46:12 +0100 Subject: [PATCH 6/8] feat(mail): Add SOGoMailHideInlineAttachments option to hide attachments when inline. Fixes #5490. Improve bracket icon. --- UI/MailerUI/UIxMailListActions.m | 54 +++++++++++++++++++++++++------- 1 file changed, 42 insertions(+), 12 deletions(-) diff --git a/UI/MailerUI/UIxMailListActions.m b/UI/MailerUI/UIxMailListActions.m index ff62f6d3c..719d326fd 100644 --- a/UI/MailerUI/UIxMailListActions.m +++ b/UI/MailerUI/UIxMailListActions.m @@ -314,24 +314,54 @@ return [[[self message] valueForKey:@"uid"] stringValue]; } +- (BOOL) parseParts: (NSArray *) parts hasAttachment:(BOOL) hasAttachment { + NSEnumerator *part; + NSDictionary *currentPart; + SOGoUserDefaults *ud; + BOOL isInline; + + ud = [[[self context] activeUser] userDefaults]; + + if ([parts count] > 1) + { + part = [parts objectEnumerator]; + while (!hasAttachment + && (currentPart = [part nextObject])) { + if ([currentPart objectForKey: @"type"] && ![[[currentPart objectForKey: @"type"] uppercaseString] hasPrefix: @"MULTIPART"]) { + isInline = currentPart && [currentPart objectForKey:@"disposition"] + && [[currentPart objectForKey:@"disposition"] objectForKey:@"type"] + && [[[[currentPart objectForKey:@"disposition"] objectForKey:@"type"] uppercaseString] isEqualToString:@"INLINE"]; + if (![ud hideInlineAttachments] || ([ud hideInlineAttachments] && !isInline)) { + hasAttachment = (([currentPart objectForKey:@"disposition"] + && [[[currentPart objectForKey:@"disposition"] allKeys] length] > 0) + || ([currentPart objectForKey:@"parameterList"] + && [[currentPart objectForKey:@"parameterList"] objectForKey:@"name"] + )); + } + } else if ([currentPart objectForKey:@"parts"]) { + hasAttachment = [self parseParts: [currentPart objectForKey:@"parts"] hasAttachment: hasAttachment]; + } + } + } + + return hasAttachment; +} + - (BOOL) hasMessageAttachment { - NSArray *parts; - NSEnumerator *dispositions; - NSDictionary *currentDisp; BOOL hasAttachment; hasAttachment = NO; - parts = [[message objectForKey: @"bodystructure"] objectForKey: @"parts"]; - if ([parts count] > 1) - { - dispositions = [[parts objectsForKey: @"disposition" - notFoundMarker: nil] objectEnumerator]; - while (!hasAttachment - && (currentDisp = [dispositions nextObject])) - hasAttachment = ([[currentDisp objectForKey: @"type"] length]); - } + NS_DURING + { + hasAttachment = [self parseParts: [[message objectForKey: @"bodystructure"] objectForKey: @"parts"] hasAttachment:hasAttachment]; + } + NS_HANDLER + { + [self logWithFormat: @"Error while parsing attachements for rendering bracket"]; + } + NS_ENDHANDLER; return hasAttachment; } From bb943e414d3fc8b71ebb169e31c261cd2dcd6d37 Mon Sep 17 00:00:00 2001 From: Hivert Quentin Date: Fri, 17 Nov 2023 15:50:41 +0100 Subject: [PATCH 7/8] fix(sogo-tool): add protection to expire-sessions if the input is not an integer --- Documentation/SOGoInstallationGuide.asciidoc | 3 +-- Tools/SOGoToolExpireUserSessions.m | 7 ++++++- 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/Documentation/SOGoInstallationGuide.asciidoc b/Documentation/SOGoInstallationGuide.asciidoc index 2db47d228..e48a43717 100644 --- a/Documentation/SOGoInstallationGuide.asciidoc +++ b/Documentation/SOGoInstallationGuide.asciidoc @@ -3515,13 +3515,12 @@ without activity for specified number of minutes. Those users will have to log i sogo-tool expire-sessions [nbMinutes] * *nbMinutes* Integer, number of minutes. All session without activity in these last minutes will be removed. -* _*Warning*_ Putting anything other that a number will be count as 0 minutes... Example: ---- sogo-tool expire-sessions #Will print usage. sogo-tool expire-sessions 160 #Will remove session which last activity is older than 160 minutes. -sogo-tool expire-sessions --help #Will remove session which last activity is older than 0 minutes. +sogo-tool expire-sessions 0 #Will remove session which last activity is older than 0 minutes. ---- sogo-tool manage-acl diff --git a/Tools/SOGoToolExpireUserSessions.m b/Tools/SOGoToolExpireUserSessions.m index aeedc00e9..9aabd1d6a 100644 --- a/Tools/SOGoToolExpireUserSessions.m +++ b/Tools/SOGoToolExpireUserSessions.m @@ -140,7 +140,12 @@ NSLog(@"Remove all sessions older than %d min", sessionExpireMinutes); - if (sessionExpireMinutes >= 0) + if (sessionExpireMinutes == 0 && ![[arguments objectAtIndex: 0] isEqualToString:@"0"]) + { + //If the input is not a number intValue return 0 so we check that's really the case + [self usage]; + } + else if (sessionExpireMinutes >= 0) { rc = [self expireUserSessionOlderThan: sessionExpireMinutes]; } From aa535247513b06804fce666fe20ebcc9bd231c1f Mon Sep 17 00:00:00 2001 From: smizrahi Date: Mon, 20 Nov 2023 11:57:08 +0100 Subject: [PATCH 8/8] feat(mail): Add SOGoMailHideInlineAttachments option to hide attachments when inline. Fixes #5490. Fix default values in sogo.conf. --- SoObjects/SOGo/SOGoDefaults.plist | 1 + UI/PreferencesUI/UIxJSONPreferences.m | 3 +++ 2 files changed, 4 insertions(+) diff --git a/SoObjects/SOGo/SOGoDefaults.plist b/SoObjects/SOGo/SOGoDefaults.plist index 0862ed18e..e5fde2443 100644 --- a/SoObjects/SOGo/SOGoDefaults.plist +++ b/SoObjects/SOGo/SOGoDefaults.plist @@ -123,6 +123,7 @@ SOGoTemplatesFolderName = "Templates"; SOGoMailComposeMessageType = "html"; SOGoMailComposeFontSize = "0"; + SOGoMailHideInlineAttachments = NO; SOGoMailDisplayRemoteInlineImages = "never"; SOGoMailCertificateEnabled = YES; diff --git a/UI/PreferencesUI/UIxJSONPreferences.m b/UI/PreferencesUI/UIxJSONPreferences.m index 3af2fdc9c..75889851e 100644 --- a/UI/PreferencesUI/UIxJSONPreferences.m +++ b/UI/PreferencesUI/UIxJSONPreferences.m @@ -368,6 +368,9 @@ static SoProduct *preferencesProduct = nil; if ([[defaults source] objectForKey: @"SOGoMailAutoMarkAsReadDelay"] == nil) [[defaults source] setObject: [NSNumber numberWithInt: [defaults mailAutoMarkAsReadDelay]] forKey: @"SOGoMailAutoMarkAsReadDelay"]; + if ([[defaults source] objectForKey: @"SOGoMailHideInlineAttachments"] == nil) + [[defaults source] setObject: [NSNumber numberWithBool: [defaults hideInlineAttachments]] forKey: @"SOGoMailHideInlineAttachments"]; + if (![[defaults source] objectForKey: @"SOGoMailAutoSave"]) [[defaults source] setObject: [defaults mailAutoSave] forKey: @"SOGoMailAutoSave"];