From 491d7aaffcc2fc2b8acb468e6387501c2af376e4 Mon Sep 17 00:00:00 2001 From: Ludovic Marcotte Date: Mon, 30 Mar 2015 09:42:32 -0400 Subject: [PATCH 01/19] improved multipart handling using EAS --- ActiveSync/NSString+ActiveSync.h | 3 ++- ActiveSync/NSString+ActiveSync.m | 12 ++++++++++++ ActiveSync/SOGoActiveSyncDispatcher.m | 3 ++- NEWS | 11 ++++++++++- 4 files changed, 26 insertions(+), 3 deletions(-) diff --git a/ActiveSync/NSString+ActiveSync.h b/ActiveSync/NSString+ActiveSync.h index 4aad558a2..963b3d00a 100644 --- a/ActiveSync/NSString+ActiveSync.h +++ b/ActiveSync/NSString+ActiveSync.h @@ -1,6 +1,6 @@ /* -Copyright (c) 2014, Inverse inc. +Copyright (c) 2014-2015, Inverse inc. All rights reserved. Redistribution and use in source and binary forms, with or without @@ -51,6 +51,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - (NSString *) command; - (NSString *) collectionid; - (NSString *) itemid; +- (BOOL) acceptsMultiPart; - (NSData *) convertHexStringToBytes; @end diff --git a/ActiveSync/NSString+ActiveSync.m b/ActiveSync/NSString+ActiveSync.m index 6aa054d10..a66f38252 100644 --- a/ActiveSync/NSString+ActiveSync.m +++ b/ActiveSync/NSString+ActiveSync.m @@ -322,6 +322,18 @@ static NSArray *easCommandParameters = nil; return s; } +- (BOOL) acceptsMultiPart +{ + NSString *s; + + s = [self _valueForParameter: @"OPTIONS="]; + + if (s && [s rangeOfString: @"AcceptMultiPart" options: NSCaseInsensitiveSearch].location != NSNotFound) + return YES; + + return NO; +} + // // FIXME: combine with our OpenChange code. diff --git a/ActiveSync/SOGoActiveSyncDispatcher.m b/ActiveSync/SOGoActiveSyncDispatcher.m index fc73a7b5e..622bdddf0 100644 --- a/ActiveSync/SOGoActiveSyncDispatcher.m +++ b/ActiveSync/SOGoActiveSyncDispatcher.m @@ -2630,7 +2630,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. aSelector = NSSelectorFromString(cmdName); // The -processItemOperations: method will generate a multipart response when Content-Type is application/vnd.ms-sync.multipart - if ([[theRequest headerForKey: @"MS-ASAcceptMultiPart"] isEqualToString:@"T"]) + if (([cmdName rangeOfString: @"ItemOperations" options: NSCaseInsensitiveSearch].location != NSNotFound) && + ([[theRequest headerForKey: @"MS-ASAcceptMultiPart"] isEqualToString:@"T"] || [[theRequest uri] acceptsMultiPart])) [theResponse setHeader: @"application/vnd.ms-sync.multipart" forKey: @"Content-Type"]; else [theResponse setHeader: @"application/vnd.ms-sync.wbxml" forKey: @"Content-Type"]; diff --git a/NEWS b/NEWS index df8209afb..38ab54e89 100644 --- a/NEWS +++ b/NEWS @@ -1,4 +1,13 @@ -2.2.17a (2014-03-15) +2.2.18 (2015-04-XX) +------------------- + +Enhancements + - improved multipart handling using EAS + +Bug fixes + - + +2.2.17a (2015-03-15) -------------------- Bug fixes From f5607b3e857270f2efdf7c28a629d93b54029d86 Mon Sep 17 00:00:00 2001 From: Ludovic Marcotte Date: Mon, 30 Mar 2015 09:49:44 -0400 Subject: [PATCH 02/19] now keep the BodyPreference for future EAS use and default to MIME if none set (#3146) --- ActiveSync/SOGoActiveSyncDispatcher+Sync.m | 46 +++++++++++++++++++--- ActiveSync/SOGoActiveSyncDispatcher.m | 3 ++ NEWS | 2 +- 3 files changed, 45 insertions(+), 6 deletions(-) diff --git a/ActiveSync/SOGoActiveSyncDispatcher+Sync.m b/ActiveSync/SOGoActiveSyncDispatcher+Sync.m index cdd4cd9d1..9c306061a 100644 --- a/ActiveSync/SOGoActiveSyncDispatcher+Sync.m +++ b/ActiveSync/SOGoActiveSyncDispatcher+Sync.m @@ -131,6 +131,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. [[o properties] removeObjectForKey: @"SyncCache"]; [[o properties] removeObjectForKey: @"DateCache"]; [[o properties] removeObjectForKey: @"MoreAvailable"]; + [[o properties] removeObjectForKey: @"BodyPreferenceType"]; [[o properties] removeObjectForKey: @"SuccessfulMoveItemsOps"]; [[o properties] addEntriesFromDictionary: values]; @@ -1068,14 +1069,14 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. changeDetected: (BOOL *) changeDetected maxSyncResponseSize: (int) theMaxSyncResponseSize { - NSString *collectionId, *realCollectionId, *syncKey, *davCollectionTag, *bodyPreferenceType, *lastServerKey, *syncKeyInCache; + NSString *collectionId, *realCollectionId, *syncKey, *davCollectionTag, *bodyPreferenceType, *mimeSupport, *lastServerKey, *syncKeyInCache; SOGoMicrosoftActiveSyncFolderType folderType; id collection, value; NSMutableString *changeBuffer, *commandsBuffer; BOOL getChanges, first_sync; unsigned int windowSize, v, status; - NSMutableDictionary *folderMetadata; + NSMutableDictionary *folderMetadata, *folderOptions; changeBuffer = [NSMutableString string]; commandsBuffer = [NSMutableString string]; @@ -1124,20 +1125,22 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. first_sync = NO; + folderMetadata = [self _folderMetadataForKey: [self _getNameInCache: collection withType: folderType]]; + if ([syncKey isEqualToString: @"0"]) { davCollectionTag = @"-1"; first_sync = YES; *changeDetected = YES; } - else if ((![syncKey isEqualToString: @"-1"]) && !([[self _folderMetadataForKey: [self _getNameInCache: collection withType: folderType]] objectForKey: @"SyncCache"])) + else if ((![syncKey isEqualToString: @"-1"]) && !([folderMetadata objectForKey: @"SyncCache"])) { //NSLog(@"Reset folder: %@", [collection nameInContainer]); davCollectionTag = @"0"; first_sync = YES; *changeDetected = YES; - if (!([[self _folderMetadataForKey: [self _getNameInCache: collection withType: folderType]] objectForKey: @"displayName"])) + if (!([folderMetadata objectForKey: @"displayName"])) status = 12; // need folderSync else status = 3; // do a complete resync @@ -1147,7 +1150,40 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. bodyPreferenceType = [[(id)[[(id)[theDocumentElement getElementsByTagName: @"BodyPreference"] lastObject] getElementsByTagName: @"Type"] lastObject] textValue]; if (!bodyPreferenceType) - bodyPreferenceType = @"1"; + { + bodyPreferenceType = [[folderMetadata objectForKey: @"FolderOptions"] objectForKey: @"BodyPreferenceType"]; + + // By default, send MIME mails. See #3146 for details. + if (!bodyPreferenceType) + bodyPreferenceType = @"4"; + } + else + { + mimeSupport = [[(id)[theDocumentElement getElementsByTagName: @"MIMESupport"] lastObject] textValue]; + + if (!mimeSupport) + mimeSupport = [[folderMetadata objectForKey: @"FolderOptions"] objectForKey: @"MIMESupport"]; + + if (!mimeSupport) + mimeSupport = @"0"; + + if ([mimeSupport isEqualToString: @"1"] && [bodyPreferenceType isEqualToString: @"4"]) + bodyPreferenceType = @"2"; + else if ([mimeSupport isEqualToString: @"2"] && [bodyPreferenceType isEqualToString: @"4"]) + bodyPreferenceType = @"4"; + else if ([mimeSupport isEqualToString: @"0"] && [bodyPreferenceType isEqualToString: @"4"]) + bodyPreferenceType = @"2"; + + + // Avoid writing to cache if there is nothing to change. + if (![[[folderMetadata objectForKey: @"FolderOptions"] objectForKey: @"BodyPreferenceType"] isEqualToString: bodyPreferenceType] || + ![[[folderMetadata objectForKey: @"FolderOptions"] objectForKey: @"MIMESupport"] isEqualToString: mimeSupport]) + { + folderOptions = [[NSDictionary alloc] initWithObjectsAndKeys: mimeSupport, @"MIMESupport", bodyPreferenceType, @"BodyPreferenceType", nil]; + [folderMetadata setObject: folderOptions forKey: @"FolderOptions"]; + [self _setFolderMetadata: folderMetadata forKey: [self _getNameInCache: collection withType: folderType]]; + } + } [context setObject: bodyPreferenceType forKey: @"BodyPreferenceType"]; diff --git a/ActiveSync/SOGoActiveSyncDispatcher.m b/ActiveSync/SOGoActiveSyncDispatcher.m index 622bdddf0..c684c3ec8 100644 --- a/ActiveSync/SOGoActiveSyncDispatcher.m +++ b/ActiveSync/SOGoActiveSyncDispatcher.m @@ -917,6 +917,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. [[o properties] removeObjectForKey: @"SyncCache"]; [[o properties] removeObjectForKey: @"DateCache"]; [[o properties] removeObjectForKey: @"MoreAvailable"]; + [[o properties] removeObjectForKey: @"BodyPreferenceType"]; [[o properties] removeObjectForKey: @"SuccessfulMoveItemsOps"]; [o save]; @@ -1001,6 +1002,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. [[o properties] removeObjectForKey: @"SyncCache"]; [[o properties] removeObjectForKey: @"DateCache"]; [[o properties] removeObjectForKey: @"MoreAvailable"]; + [[o properties] removeObjectForKey: @"BodyPreferenceType"]; [[o properties] removeObjectForKey: @"SuccessfulMoveItemsOps"]; } @@ -1023,6 +1025,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. [[o properties] removeObjectForKey: @"SyncCache"]; [[o properties] removeObjectForKey: @"DateCache"]; [[o properties] removeObjectForKey: @"MoreAvailable"]; + [[o properties] removeObjectForKey: @"BodyPreferenceType"]; [[o properties] removeObjectForKey: @"SuccessfulMoveItemsOps"]; } diff --git a/NEWS b/NEWS index 38ab54e89..7280a512b 100644 --- a/NEWS +++ b/NEWS @@ -5,7 +5,7 @@ Enhancements - improved multipart handling using EAS Bug fixes - - + - now keep the BodyPreference for future EAS use and default to MIME if none set (#3146) 2.2.17a (2015-03-15) -------------------- From c428ac255337739856833fe96d56fb82ab8df977 Mon Sep 17 00:00:00 2001 From: Ludovic Marcotte Date: Mon, 30 Mar 2015 09:57:27 -0400 Subject: [PATCH 03/19] EAS reply fix when message/rfc822 parts are included in the original mail (#3153) --- ActiveSync/SOGoMailObject+ActiveSync.m | 4 ++++ NEWS | 1 + 2 files changed, 5 insertions(+) diff --git a/ActiveSync/SOGoMailObject+ActiveSync.m b/ActiveSync/SOGoMailObject+ActiveSync.m index 45c865c84..d8aa6e0f9 100644 --- a/ActiveSync/SOGoMailObject+ActiveSync.m +++ b/ActiveSync/SOGoMailObject+ActiveSync.m @@ -224,6 +224,10 @@ struct GlobalObjectId { while ((key = [e nextObject])) { + // don't use body parts from a nested body - e.g. body of type message/rfc822 + if (![key hasPrefix: @"1"]) + continue; + part = [self lookupInfoForBodyPart: key]; type = [part valueForKey: @"type"]; subtype = [part valueForKey: @"subtype"]; diff --git a/NEWS b/NEWS index 7280a512b..2b2149d13 100644 --- a/NEWS +++ b/NEWS @@ -6,6 +6,7 @@ Enhancements Bug fixes - now keep the BodyPreference for future EAS use and default to MIME if none set (#3146) + - EAS reply fix when message/rfc822 parts are included in the original mail (#3153) 2.2.17a (2015-03-15) -------------------- From db9536adcc5f57fa1596c8ed6efbcdf0b349d664 Mon Sep 17 00:00:00 2001 From: Ludovic Marcotte Date: Tue, 31 Mar 2015 09:25:57 -0400 Subject: [PATCH 04/19] (fix) fix yet an other potential crash during freebusy lookups during timezone changes --- NEWS | 1 + UI/MainUI/SOGoUserHomePage.m | 24 +++++++++++++----------- 2 files changed, 14 insertions(+), 11 deletions(-) diff --git a/NEWS b/NEWS index 2b2149d13..708fc7f59 100644 --- a/NEWS +++ b/NEWS @@ -7,6 +7,7 @@ Enhancements Bug fixes - now keep the BodyPreference for future EAS use and default to MIME if none set (#3146) - EAS reply fix when message/rfc822 parts are included in the original mail (#3153) + - fix yet an other potential crash during freebusy lookups during timezone changes 2.2.17a (2015-03-15) -------------------- diff --git a/UI/MainUI/SOGoUserHomePage.m b/UI/MainUI/SOGoUserHomePage.m index c6223e656..42f373f8d 100644 --- a/UI/MainUI/SOGoUserHomePage.m +++ b/UI/MainUI/SOGoUserHomePage.m @@ -52,7 +52,9 @@ #import -#define intervalSeconds 900 /* 15 minutes */ +#define INTERVALSECONDS 900 /* 15 minutes */ +#define PADDING 8 +#define HALFPADDING PADDING/2 @interface SOGoUserHomePage : UIxComponent @@ -151,23 +153,23 @@ startInterval = 0; else startInterval = ([currentDate timeIntervalSinceDate: startDate] - / intervalSeconds); + / INTERVALSECONDS); delta = [[currentDate timeZoneDetail] timeZoneSecondsFromGMT] - [[startDate timeZoneDetail] timeZoneSecondsFromGMT]; - startInterval += (delta/60/15); - startInterval = (startInterval < -4 ? -4 : startInterval); + startInterval += (delta/INTERVALSECONDS); + startInterval = (startInterval < -(HALFPADDING) ? -(HALFPADDING) : startInterval); currentDate = [record objectForKey: @"endDate"]; if ([currentDate earlierDate: endDate] == endDate) endInterval = itemCount - 1; else endInterval = ([currentDate timeIntervalSinceDate: startDate] - / intervalSeconds); + / INTERVALSECONDS); delta = [[currentDate timeZoneDetail] timeZoneSecondsFromGMT] - [[startDate timeZoneDetail] timeZoneSecondsFromGMT]; - endInterval += (delta/60/15); + endInterval += (delta/INTERVALSECONDS); endInterval = (endInterval < 0 ? 0 : endInterval); - endInterval = (endInterval > itemCount+4 ? itemCount+4 : endInterval); + endInterval = (endInterval > itemCount+HALFPADDING ? itemCount+HALFPADDING : endInterval); // Update bit string representation // If the user is a resource with restristed amount of bookings, keep the sum of overlapping events @@ -230,19 +232,19 @@ // Slices of 15 minutes. The +8 is to take into account that we can // have a timezone change during the freebusy lookup. We have +4 at the // beginning and +4 at the end. - intervals = interval / intervalSeconds + 8; + intervals = interval / INTERVALSECONDS + PADDING; // Build a bit string representation of the freebusy data for the period freeBusyItems = calloc(intervals, sizeof (unsigned int)); - [self _fillFreeBusyItems: (freeBusyItems+4) - count: (intervals-4) + [self _fillFreeBusyItems: (freeBusyItems+HALFPADDING) + count: (intervals-PADDING) withRecords: [fb fetchFreeBusyInfosFrom: start to: end forContact: uid] fromStartDate: startDate toEndDate: endDate]; // Convert bit string to a NSArray. We also skip by the default the non-requested information. freeBusy = [NSMutableArray arrayWithCapacity: intervals]; - for (count = 4; count < (intervals-4); count++) + for (count = HALFPADDING; count < (intervals-HALFPADDING); count++) { [freeBusy addObject: [NSString stringWithFormat: @"%d", *(freeBusyItems + count)]]; } From 784f0100e9d4dc55d5320e41eecfc3a7e68f9943 Mon Sep 17 00:00:00 2001 From: peruchi Date: Tue, 31 Mar 2015 14:18:23 -0300 Subject: [PATCH 05/19] Create sogo-systemd-redhat.spec --- packaging/rhel/sogo-systemd-redhat.spec | 465 ++++++++++++++++++++++++ 1 file changed, 465 insertions(+) create mode 100644 packaging/rhel/sogo-systemd-redhat.spec diff --git a/packaging/rhel/sogo-systemd-redhat.spec b/packaging/rhel/sogo-systemd-redhat.spec new file mode 100644 index 000000000..e17f917e3 --- /dev/null +++ b/packaging/rhel/sogo-systemd-redhat.spec @@ -0,0 +1,465 @@ +# We disable OpenChange builds on el5 since it's prehistoric +%define enable_openchange 1 +%{?el5:%define enable_openchange 0} +%{?el7:%define enable_openchange 0} + +%ifarch %ix86 +%define enable_openchange 0 +%endif + +%{!?sogo_major_version: %global sogo_major_version %(/bin/echo %{sogo_version} | /bin/cut -f 1 -d .)} +%if %enable_openchange +%global oc_build_depends samba4 openchange +%endif + +%{!?python_sys_pyver: %global python_sys_pyver %(/usr/bin/python -c "import sys; print sys.hexversion")} + +%define sogo_user sogo + +Summary: SOGo +Name: sogo +Version: %{sogo_version} +Release: %{dist_suffix}%{?dist} +Vendor: http://www.inverse.ca/ +Packager: Inverse inc. +License: GPL +URL: http://www.inverse.ca/contributions/sogo.html +Group: Productivity/Groupware +Source: SOGo-%{sogo_version}.tar.gz +Prefix: /usr +AutoReqProv: off +Requires: gnustep-base >= 1.23, sope%{sope_major_version}%{sope_minor_version}-core, httpd, sope%{sope_major_version}%{sope_minor_version}-core, sope%{sope_major_version}%{sope_minor_version}-appserver, sope%{sope_major_version}%{sope_minor_version}-ldap, sope%{sope_major_version}%{sope_minor_version}-cards >= %{sogo_version}, sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore >= %{sogo_version}, sope%{sope_major_version}%{sope_minor_version}-sbjson, libmemcached, memcached, tmpwatch, zip +BuildRoot: %{_tmppath}/%{name}-%{version}-%{release} +BuildRequires: gcc-objc gnustep-base gnustep-make sope%{sope_major_version}%{sope_minor_version}-appserver-devel sope%{sope_major_version}%{sope_minor_version}-core-devel sope%{sope_major_version}%{sope_minor_version}-ldap-devel sope%{sope_major_version}%{sope_minor_version}-mime-devel sope%{sope_major_version}%{sope_minor_version}-xml-devel sope%{sope_major_version}%{sope_minor_version}-gdl1-devel sope%{sope_major_version}%{sope_minor_version}-sbjson-devel libmemcached-devel sed %{?oc_build_depends} + + +# Required by MS Exchange freebusy lookups +%{?el5:Requires: curl} +%{?el5:BuildRequires: curl-devel} +%{?el6:Requires: libcurl} +%{?el6:BuildRequires: libcurl-devel} + +# saml is enabled everywhere except on el5 since its glib2 is prehistoric +%define saml2_cfg_opts "--enable-saml2" +%{?el5:%define saml2_cfg_opts ""} +%{?el7:%define saml2_cfg_opts ""} +%{?el6:Requires: lasso} +%{?el6:BuildRequires: lasso-devel} + +%description +SOGo is a groupware server built around OpenGroupware.org (OGo) and +the SOPE application server. It focuses on scalability. + +The Inverse edition of this project has many feature enhancements: +- CalDAV and GroupDAV compliance +- full handling of vCard as well as vCalendar/iCalendar formats +- support for folder sharing and ACLs + +The Web interface has been rewritten in an AJAX fashion to provided a faster +UI for the users, consistency in look and feel with the Mozilla applications, +and to reduce the load of the transactions on the server. + +%package -n sogo-tool +Summary: Command-line toolsuite for SOGo +Group: Productivity/Groupware +Requires: sogo = %{sogo_version} +AutoReqProv: off + +%description -n sogo-tool +Administrative tool for SOGo that provides the following internal commands: + backup -- backup user folders + restore -- restore user folders + remove-doubles -- remove duplicate contacts from the user addressbooks + check-doubles -- list user addressbooks with duplicate contacts + +%package -n sogo-slapd-sockd +Summary: SOGo backend for slapd and back-sock +Group: Productivity/Groupware +AutoReqProv: off + +%description -n sogo-slapd-sockd +SOGo backend for slapd and back-sock, enabling access to private addressbooks +via LDAP. + +%package -n sogo-ealarms-notify +Summary: SOGo utility for executing email alarms +Group: Productivity/Groupware +AutoReqProv: off + +%description -n sogo-ealarms-notify +SOGo utility executed each minute via a cronjob for executing email alarms. + +%package -n sogo-activesync +Summary: SOGo module to handle ActiveSync requests +Group: Productivity/Groupware +Requires: libwbxml, sogo = %{sogo_version} +BuildRequires: libwbxml-devel +AutoReqProv: off + +%description -n sogo-activesync +SOGo module to handle ActiveSync requests + +%package -n sogo-devel +Summary: Development headers and libraries for SOGo +Group: Development/Libraries/Objective C +AutoReqProv: off + +%description -n sogo-devel +Development headers and libraries for SOGo. Needed to create modules. + +%package -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore +Summary: Storage backend for folder abstraction. +Group: Development/Libraries/Objective C +Requires: sope%{sope_major_version}%{sope_minor_version}-gdl1 +AutoReqProv: off + +%description -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore +The storage backend implements the "low level" folder abstraction, which is +basically an arbitary "BLOB" containing some document. + +SOPE is a framework for developing web applications and services. The +name "SOPE" (SKYRiX Object Publishing Environment) is inspired by ZOPE. + +%package -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore-devel +Summary: Development files for the GNUstep database libraries +Group: Development/Libraries/Objective C +Requires: sope%{sope_major_version}%{sope_minor_version}-gdl1 +AutoReqProv: off + +%description -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore-devel +This package contains the header files for SOPE's GDLContentStore library. + +SOPE is a framework for developing web applications and services. The +name "SOPE" (SKYRiX Object Publishing Environment) is inspired by ZOPE. + +%package -n sope%{sope_major_version}%{sope_minor_version}-cards +Summary: SOPE versit parsing library for iCal and VCard formats +Group: Development/Libraries/Objective C +AutoReqProv: off + +%description -n sope%{sope_major_version}%{sope_minor_version}-cards +SOPE versit parsing library for iCal and VCard formats + +%package -n sope%{sope_major_version}%{sope_minor_version}-cards-devel +Summary: SOPE versit parsing library for iCal and VCard formats +Group: Development/Libraries/Objective C +Requires: sope%{sope_major_version}%{sope_minor_version}-cards +AutoReqProv: off + +%description -n sope%{sope_major_version}%{sope_minor_version}-cards-devel +SOPE versit parsing library for iCal and VCard formats + +%if %enable_openchange +%package openchange-backend +Summary: SOGo backend for OpenChange +Group: Productivity/Groupware +AutoReqProv: off + +%description openchange-backend +SOGo backend for OpenChange +%endif + +######################################## +%prep +rm -fr ${RPM_BUILD_ROOT} +%setup -q -n SOGo-%{sogo_version} + + +# small tweak to the python script for RHEL5 +# if hex(sys.hexversion) < 0x02060000 +%if %{python_sys_pyver} < 33947648 + sed -i 's!/usr/bin/env python!/usr/bin/env python2.6!' Scripts/openchange_user_cleanup +%endif + + +# ****************************** build ******************************** +%build +%if 0%{?el7} +. /usr/lib64/GNUstep/Makefiles/GNUstep.sh +%else +. /usr/share/GNUstep/Makefiles/GNUstep.sh +%endif +./configure %saml2_cfg_opts + +case %{_target_platform} in +ppc64-*) + cc="gcc -m64"; + ldflags="-m64";; +*) + cc="gcc"; + ldflags="";; +esac + +make CC="$cc" LDFLAGS="$ldflags" messages=yes + +# OpenChange +%if %{sogo_major_version} >= 2 +(cd OpenChange; \ + LD_LIBRARY_PATH=../SOPE/NGCards/obj:../SOPE/GDLContentStore/obj \ + make GNUSTEP_INSTALLATION_DOMAIN=SYSTEM ) +%endif + +# ****************************** install ****************************** +%install +QA_SKIP_BUILD_ROOT=1 +export QA_SKIP_BUILD_ROOT + +case %{_target_platform} in +ppc64-*) + cc="gcc -m64"; + ldflags="-m64";; +*) + cc="gcc"; + ldflags="";; +esac + +make DESTDIR=${RPM_BUILD_ROOT} \ + GNUSTEP_INSTALLATION_DOMAIN=SYSTEM \ + CC="$cc" LDFLAGS="$ldflags" \ + install +install -d ${RPM_BUILD_ROOT}/usr/lib/systemd/system/ +install -d ${RPM_BUILD_ROOT}/etc/cron.d +install -d ${RPM_BUILD_ROOT}/etc/cron.daily +install -d ${RPM_BUILD_ROOT}/etc/logrotate.d +install -d ${RPM_BUILD_ROOT}/etc/sysconfig +install -d ${RPM_BUILD_ROOT}/etc/httpd/conf.d +install -d ${RPM_BUILD_ROOT}/usr/sbin +install -d ${RPM_BUILD_ROOT}/var/lib/sogo +install -d ${RPM_BUILD_ROOT}/var/log/sogo +install -d ${RPM_BUILD_ROOT}/var/run/sogo +install -d ${RPM_BUILD_ROOT}/var/spool/sogo +install -d -m 750 -o %sogo_user -g %sogo_user ${RPM_BUILD_ROOT}/etc/sogo +install -m 640 -o %sogo_user -g %sogo_user Scripts/sogo.conf ${RPM_BUILD_ROOT}/etc/sogo/ +install -m 755 Scripts/openchange_user_cleanup ${RPM_BUILD_ROOT}/%{_sbindir} +cat Apache/SOGo.conf | sed -e "s@/lib/@/%{_lib}/@g" > ${RPM_BUILD_ROOT}/etc/httpd/conf.d/SOGo.conf +install -m 600 Scripts/sogo.cron ${RPM_BUILD_ROOT}/etc/cron.d/sogo +cp Scripts/tmpwatch ${RPM_BUILD_ROOT}/etc/cron.daily/sogo-tmpwatch +chmod 755 ${RPM_BUILD_ROOT}/etc/cron.daily/sogo-tmpwatch +cp Scripts/logrotate ${RPM_BUILD_ROOT}/etc/logrotate.d/sogo +cp Scripts/sogo-systemd-redhat ${RPM_BUILD_ROOT}/usr/lib/systemd/system/sogod.service +chmod 644 ${RPM_BUILD_ROOT}/usr/lib/systemd/system/sogod.service +cp Scripts/sogo-default ${RPM_BUILD_ROOT}/etc/sysconfig/sogo +rm -rf ${RPM_BUILD_ROOT}%{_bindir}/test_quick_extract + +# OpenChange +%if %{sogo_major_version} >= 2 +(cd OpenChange; \ + LD_LIBRARY_PATH=${RPM_BUILD_ROOT}%{_libdir} \ + make DESTDIR=${RPM_BUILD_ROOT} \ + GNUSTEP_INSTALLATION_DOMAIN=SYSTEM \ + CC="$cc" LDFLAGS="$ldflags" \ + install) +%endif + +# ActiveSync +(cd ActiveSync; \ + LD_LIBRARY_PATH=${RPM_BUILD_ROOT}%{_libdir} \ + make DESTDIR=${RPM_BUILD_ROOT} \ + GNUSTEP_INSTALLATION_DOMAIN=SYSTEM \ + CC="$cc" LDFLAGS="$ldflags" \ + install) + +# ****************************** clean ******************************** +%clean +rm -fr ${RPM_BUILD_ROOT} + +# ****************************** files ******************************** +%files -n sogo +%defattr(-,root,root,-) + +/etc/init.d/sogod +/etc/cron.daily/sogo-tmpwatch +%dir %attr(0700, %sogo_user, %sogo_user) %{_var}/lib/sogo +%dir %attr(0700, %sogo_user, %sogo_user) %{_var}/log/sogo +%dir %attr(0755, %sogo_user, %sogo_user) %{_var}/run/sogo +%dir %attr(0700, %sogo_user, %sogo_user) %{_var}/spool/sogo +%dir %attr(0750, root, %sogo_user) %{_sysconfdir}/sogo +%{_sbindir}/sogod +%{_sbindir}/openchange_user_cleanup +%{_libdir}/sogo/libSOGo.so* +%{_libdir}/sogo/libSOGoUI.so* +%{_libdir}/GNUstep/SOGo/AdministrationUI.SOGo +%{_libdir}/GNUstep/SOGo/Appointments.SOGo +%{_libdir}/GNUstep/SOGo/CommonUI.SOGo +%{_libdir}/GNUstep/SOGo/Contacts.SOGo +%{_libdir}/GNUstep/SOGo/ContactsUI.SOGo +%{_libdir}/GNUstep/SOGo/MailPartViewers.SOGo +%{_libdir}/GNUstep/SOGo/Mailer.SOGo +%{_libdir}/GNUstep/SOGo/MailerUI.SOGo +%{_libdir}/GNUstep/SOGo/MainUI.SOGo +%{_libdir}/GNUstep/SOGo/PreferencesUI.SOGo +%{_libdir}/GNUstep/SOGo/SchedulerUI.SOGo + +%{_libdir}/GNUstep/Frameworks/SOGo.framework/Resources +%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/%{sogo_major_version}/sogo/libSOGo.so* +%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/%{sogo_major_version}/Resources +%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/Current +%{_libdir}/GNUstep/SOGo/Templates +%{_libdir}/GNUstep/SOGo/WebServerResources +%{_libdir}/GNUstep/OCSTypeModels +%{_libdir}/GNUstep/WOxElemBuilders-* + +%config(noreplace) %attr(0640, root, %sogo_user) %{_sysconfdir}/sogo/sogo.conf +%config(noreplace) %{_sysconfdir}/logrotate.d/sogo +%config(noreplace) %{_sysconfdir}/cron.d/sogo +%config(noreplace) %{_sysconfdir}/httpd/conf.d/SOGo.conf +%config(noreplace) %{_sysconfdir}/sysconfig/sogo +%doc ChangeLog NEWS Scripts/*sh Scripts/updates.php Apache/SOGo-apple-ab.conf + +%files -n sogo-tool +%{_sbindir}/sogo-tool + +%files -n sogo-ealarms-notify +%{_sbindir}/sogo-ealarms-notify + +%files -n sogo-slapd-sockd +%{_sbindir}/sogo-slapd-sockd + +%files -n sogo-activesync +%{_libdir}/GNUstep/SOGo/ActiveSync.SOGo +%doc ActiveSync/LICENSE ActiveSync/README + +%files -n sogo-devel +%{_includedir}/SOGo +%{_includedir}/SOGoUI +%{_libdir}/sogo/libSOGo.so* +%{_libdir}/sogo/libSOGoUI.so* +%{_libdir}/GNUstep/Frameworks/SOGo.framework/Headers +%{_libdir}/GNUstep/Frameworks/SOGo.framework/sogo/libSOGo.so +%{_libdir}/GNUstep/Frameworks/SOGo.framework/sogo/SOGo +%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/%{sogo_major_version}/Headers +%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/%{sogo_major_version}/sogo/libSOGo.so* +%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/%{sogo_major_version}/sogo/SOGo + +%files -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore +%defattr(-,root,root,-) +%{_libdir}/sogo/libGDLContentStore*.so* + +%files -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore-devel +%{_includedir}/GDLContentStore +%{_libdir}/sogo/libGDLContentStore*.so* + +%files -n sope%{sope_major_version}%{sope_minor_version}-cards +%{_libdir}/sogo/libNGCards.so* +%{_libdir}/GNUstep/SaxDrivers-* +%{_libdir}/GNUstep/SaxMappings +%{_libdir}/GNUstep/Libraries/Resources/NGCards + +%files -n sope%{sope_major_version}%{sope_minor_version}-cards-devel +%{_includedir}/NGCards +%{_libdir}/sogo/libNGCards.so* + +%if %enable_openchange +%files openchange-backend +%defattr(-,root,root,-) +%{_libdir}/GNUstep/SOGo/*.MAPIStore +%{_libdir}/mapistore_backends/* +%endif + +# **************************** pkgscripts ***************************** +%pre +if ! id %sogo_user >& /dev/null; then + /usr/sbin/useradd -d %{_var}/lib/sogo -c "SOGo daemon" -s /sbin/nologin -M -r %sogo_user +fi + +%post +# update timestamp on imgs,css,js to let apache know the files changed +find %{_libdir}/GNUstep/SOGo/WebServerResources -exec touch {} \; +systemctl enable sogod +systemctl start sogod > /dev/null 2>&1 + +%preun +if [ "$1" == "0" ] +then + systemctl disable sogod + systemctl stop sogod > /dev/null 2>&1 +fi + +%postun +if test "$1" = "0" +then + /usr/sbin/userdel %sogo_user + /usr/sbin/groupdel %sogo_user > /dev/null 2>&1 + /bin/rm -rf %{_var}/run/sogo + /bin/rm -rf %{_var}/spool/sogo + # not removing /var/lib/sogo to keep .GNUstepDefaults +fi + +# ********************************* changelog ************************* +%changelog +* Thu Mar 31 2015. Inverse inc. +- Change script start sogod for systemd + +* Wed Oct 8 2014 Inverse inc. +- fixed the library move to "sogo" app dir + +* Wed Jan 15 2014 Inverse inc. +- New package: sogo-activesync +- explicitly list all *.SOGo modules in sogo package +- added dependency on sogo = %version for sogo-tool + +* Thu Apr 17 2013 Inverse inc. +- Install openchange_user_cleanup in sbindir instead of doc + +* Wed Apr 10 2013 Inverse inc. +- use %sogo_user instead of 'sogo' +- install a sample sogo.conf in /etc/sogo + +* Tue Jan 22 2013 Inverse inc. +- Create the sogo user as a system user +- Use %attr() to set directory permissions instead of chown/chmod + +* Mon Nov 12 2012 Inverse inc. +- Add missing dependency on lasso and lasso-devel + +* Mon Nov 05 2012 Inverse inc. +- Disable saml2 on rhel5 - glib2 too old + +* Fri Nov 02 2012 Inverse inc. +- Enable saml2 + +* Tue Aug 28 2012 Inverse inc. +- Add openchange_cleanup.py and tweak it to work on RHEL5 + +* Tue Jul 31 2012 Inverse inc. +- treat logrotate file as a config file + +* Fri May 24 2012 Inverse inc. +- %post: restart sogo if it was running before rpm install + +* Fri Mar 16 2012 Inverse inc. +- %post: update timestamp on imgs,css,js to let apache know the files changed + +* Fri Feb 16 2012 Inverse inc. +- Use globbing to include all sql upgrade scripts instead of listing them all + +* Tue Jan 10 2012 Inverse inc. +- /etc/cron.d/sogo + +* Thu Oct 27 2011 Inverse inc. +- make build of sogo-openchange-backend conditional to sogo_version >= 2 + +* Fri Oct 14 2011 Inverse inc. +- adapted to gnustep-make 2.6 +- added sogo-openchange-backend + +* Tue Sep 28 2010 Inverse inc. +- removed "README" from documentation + +* Fri Aug 20 2010 Inverse inc. +- added sogo-ealarms-notify package + +* Tue Apr 06 2010 Inverse inc. +- added sogo-slapd-sockd package + +* Thu Jul 31 2008 Inverse inc. +- added dependencies on sopeXY-appserver, -core, -gdl1-contentstore and -ldap + +* Wed May 21 2008 Inverse inc. +- removed installation of template and resource files, since it is now done by the upstream package + +* Tue Oct 4 2007 Inverse inc. +- added package sope-gdl1-contentstore + +* Wed Jul 18 2007 Inverse inc. +- initial build From 36a70b161c32653cf8d7f2bdf83c6d0c4aac9b76 Mon Sep 17 00:00:00 2001 From: peruchi Date: Tue, 31 Mar 2015 14:19:16 -0300 Subject: [PATCH 06/19] Create sogo-systemd-redhat --- Scripts/sogo-systemd-redhat | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 Scripts/sogo-systemd-redhat diff --git a/Scripts/sogo-systemd-redhat b/Scripts/sogo-systemd-redhat new file mode 100644 index 000000000..7fdd56b96 --- /dev/null +++ b/Scripts/sogo-systemd-redhat @@ -0,0 +1,12 @@ +[Unit] +Description=SOGo is a groupware server +After=network.target + +[Service] +Type=forking +ExecStart=/usr/sbin/sogod -WOWorkersCount 3 -WOPidFile /var/run/sogo/sogo.pid -WOLogFile /var/log/sogo/sogo.log +PIDFile=/var/run/sogo/sogo.pid +User=sogo + +[Install] +WantedBy=multi-user.target From c9ec636a533836ec8464acadea97dc09276d2557 Mon Sep 17 00:00:00 2001 From: peruchi Date: Tue, 31 Mar 2015 14:36:04 -0300 Subject: [PATCH 07/19] Update sogo.spec --- packaging/rhel/sogo.spec | 47 ++++++++++++++++++++++++++++++++++------ 1 file changed, 40 insertions(+), 7 deletions(-) diff --git a/packaging/rhel/sogo.spec b/packaging/rhel/sogo.spec index 8f275e956..33afa3f1a 100644 --- a/packaging/rhel/sogo.spec +++ b/packaging/rhel/sogo.spec @@ -14,6 +14,13 @@ %{!?python_sys_pyver: %global python_sys_pyver %(/usr/bin/python -c "import sys; print sys.hexversion")} +# Systemd for fedora >= 17 or el 7 +%if 0%{?fedora} >= 17 || 0%{?rhel} >= 7 + %global _with_systemd 1 +%else + %global _with_systemd 0 +%endif + %define sogo_user sogo Summary: SOGo @@ -217,7 +224,13 @@ make DESTDIR=${RPM_BUILD_ROOT} \ GNUSTEP_INSTALLATION_DOMAIN=SYSTEM \ CC="$cc" LDFLAGS="$ldflags" \ install -install -d ${RPM_BUILD_ROOT}/etc/init.d + +%if 0%{?_with_systemd} + install -d ${RPM_BUILD_ROOT}/usr/lib/systemd/system/ +%else + install -d ${RPM_BUILD_ROOT}/etc/init.d +%endif + install -d ${RPM_BUILD_ROOT}/etc/cron.d install -d ${RPM_BUILD_ROOT}/etc/cron.daily install -d ${RPM_BUILD_ROOT}/etc/logrotate.d @@ -236,8 +249,15 @@ install -m 600 Scripts/sogo.cron ${RPM_BUILD_ROOT}/etc/cron.d/sogo cp Scripts/tmpwatch ${RPM_BUILD_ROOT}/etc/cron.daily/sogo-tmpwatch chmod 755 ${RPM_BUILD_ROOT}/etc/cron.daily/sogo-tmpwatch cp Scripts/logrotate ${RPM_BUILD_ROOT}/etc/logrotate.d/sogo -cp Scripts/sogo-init.d-redhat ${RPM_BUILD_ROOT}/etc/init.d/sogod -chmod 755 ${RPM_BUILD_ROOT}/etc/init.d/sogod + +%if 0%{?_with_systemd} + cp Scripts/sogo-systemd-redhat ${RPM_BUILD_ROOT}/usr/lib/systemd/system/sogod.service + chmod 644 ${RPM_BUILD_ROOT}/usr/lib/systemd/system/sogod.service +%else + cp Scripts/sogo-init.d-redhat ${RPM_BUILD_ROOT}/etc/init.d/sogod + chmod 755 ${RPM_BUILD_ROOT}/etc/init.d/sogod +%endif + cp Scripts/sogo-default ${RPM_BUILD_ROOT}/etc/sysconfig/sogo rm -rf ${RPM_BUILD_ROOT}%{_bindir}/test_quick_extract @@ -365,14 +385,24 @@ fi %post # update timestamp on imgs,css,js to let apache know the files changed find %{_libdir}/GNUstep/SOGo/WebServerResources -exec touch {} \; -/sbin/chkconfig --add sogod -/etc/init.d/sogod condrestart >&/dev/null +%if 0%{?_with_systemd} + systemctl enable sogod + systemctl start sogod > /dev/null 2>&1 +%else + /sbin/chkconfig --add sogod + /etc/init.d/sogod condrestart >&/dev/null +%endif %preun if [ "$1" == "0" ] then - /sbin/chkconfig --del sogod - /sbin/service sogod stop > /dev/null 2>&1 + %if 0%{?_with_systemd} + systemctl disable sogod + systemctl stop sogod > /dev/null 2>&1 + %else + /sbin/chkconfig --del sogod + /sbin/service sogod stop > /dev/null 2>&1 + %endif fi %postun @@ -387,6 +417,9 @@ fi # ********************************* changelog ************************* %changelog +* Thu Mar 31 2015. Inverse inc. +- Change script start sogod for systemd + * Wed Oct 8 2014 Inverse inc. - fixed the library move to "sogo" app dir From 06ef3fe8564729d971b50822e1669372324600c1 Mon Sep 17 00:00:00 2001 From: peruchi Date: Tue, 31 Mar 2015 14:37:35 -0300 Subject: [PATCH 08/19] Delete sogo-systemd-redhat.spec --- packaging/rhel/sogo-systemd-redhat.spec | 465 ------------------------ 1 file changed, 465 deletions(-) delete mode 100644 packaging/rhel/sogo-systemd-redhat.spec diff --git a/packaging/rhel/sogo-systemd-redhat.spec b/packaging/rhel/sogo-systemd-redhat.spec deleted file mode 100644 index e17f917e3..000000000 --- a/packaging/rhel/sogo-systemd-redhat.spec +++ /dev/null @@ -1,465 +0,0 @@ -# We disable OpenChange builds on el5 since it's prehistoric -%define enable_openchange 1 -%{?el5:%define enable_openchange 0} -%{?el7:%define enable_openchange 0} - -%ifarch %ix86 -%define enable_openchange 0 -%endif - -%{!?sogo_major_version: %global sogo_major_version %(/bin/echo %{sogo_version} | /bin/cut -f 1 -d .)} -%if %enable_openchange -%global oc_build_depends samba4 openchange -%endif - -%{!?python_sys_pyver: %global python_sys_pyver %(/usr/bin/python -c "import sys; print sys.hexversion")} - -%define sogo_user sogo - -Summary: SOGo -Name: sogo -Version: %{sogo_version} -Release: %{dist_suffix}%{?dist} -Vendor: http://www.inverse.ca/ -Packager: Inverse inc. -License: GPL -URL: http://www.inverse.ca/contributions/sogo.html -Group: Productivity/Groupware -Source: SOGo-%{sogo_version}.tar.gz -Prefix: /usr -AutoReqProv: off -Requires: gnustep-base >= 1.23, sope%{sope_major_version}%{sope_minor_version}-core, httpd, sope%{sope_major_version}%{sope_minor_version}-core, sope%{sope_major_version}%{sope_minor_version}-appserver, sope%{sope_major_version}%{sope_minor_version}-ldap, sope%{sope_major_version}%{sope_minor_version}-cards >= %{sogo_version}, sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore >= %{sogo_version}, sope%{sope_major_version}%{sope_minor_version}-sbjson, libmemcached, memcached, tmpwatch, zip -BuildRoot: %{_tmppath}/%{name}-%{version}-%{release} -BuildRequires: gcc-objc gnustep-base gnustep-make sope%{sope_major_version}%{sope_minor_version}-appserver-devel sope%{sope_major_version}%{sope_minor_version}-core-devel sope%{sope_major_version}%{sope_minor_version}-ldap-devel sope%{sope_major_version}%{sope_minor_version}-mime-devel sope%{sope_major_version}%{sope_minor_version}-xml-devel sope%{sope_major_version}%{sope_minor_version}-gdl1-devel sope%{sope_major_version}%{sope_minor_version}-sbjson-devel libmemcached-devel sed %{?oc_build_depends} - - -# Required by MS Exchange freebusy lookups -%{?el5:Requires: curl} -%{?el5:BuildRequires: curl-devel} -%{?el6:Requires: libcurl} -%{?el6:BuildRequires: libcurl-devel} - -# saml is enabled everywhere except on el5 since its glib2 is prehistoric -%define saml2_cfg_opts "--enable-saml2" -%{?el5:%define saml2_cfg_opts ""} -%{?el7:%define saml2_cfg_opts ""} -%{?el6:Requires: lasso} -%{?el6:BuildRequires: lasso-devel} - -%description -SOGo is a groupware server built around OpenGroupware.org (OGo) and -the SOPE application server. It focuses on scalability. - -The Inverse edition of this project has many feature enhancements: -- CalDAV and GroupDAV compliance -- full handling of vCard as well as vCalendar/iCalendar formats -- support for folder sharing and ACLs - -The Web interface has been rewritten in an AJAX fashion to provided a faster -UI for the users, consistency in look and feel with the Mozilla applications, -and to reduce the load of the transactions on the server. - -%package -n sogo-tool -Summary: Command-line toolsuite for SOGo -Group: Productivity/Groupware -Requires: sogo = %{sogo_version} -AutoReqProv: off - -%description -n sogo-tool -Administrative tool for SOGo that provides the following internal commands: - backup -- backup user folders - restore -- restore user folders - remove-doubles -- remove duplicate contacts from the user addressbooks - check-doubles -- list user addressbooks with duplicate contacts - -%package -n sogo-slapd-sockd -Summary: SOGo backend for slapd and back-sock -Group: Productivity/Groupware -AutoReqProv: off - -%description -n sogo-slapd-sockd -SOGo backend for slapd and back-sock, enabling access to private addressbooks -via LDAP. - -%package -n sogo-ealarms-notify -Summary: SOGo utility for executing email alarms -Group: Productivity/Groupware -AutoReqProv: off - -%description -n sogo-ealarms-notify -SOGo utility executed each minute via a cronjob for executing email alarms. - -%package -n sogo-activesync -Summary: SOGo module to handle ActiveSync requests -Group: Productivity/Groupware -Requires: libwbxml, sogo = %{sogo_version} -BuildRequires: libwbxml-devel -AutoReqProv: off - -%description -n sogo-activesync -SOGo module to handle ActiveSync requests - -%package -n sogo-devel -Summary: Development headers and libraries for SOGo -Group: Development/Libraries/Objective C -AutoReqProv: off - -%description -n sogo-devel -Development headers and libraries for SOGo. Needed to create modules. - -%package -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore -Summary: Storage backend for folder abstraction. -Group: Development/Libraries/Objective C -Requires: sope%{sope_major_version}%{sope_minor_version}-gdl1 -AutoReqProv: off - -%description -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore -The storage backend implements the "low level" folder abstraction, which is -basically an arbitary "BLOB" containing some document. - -SOPE is a framework for developing web applications and services. The -name "SOPE" (SKYRiX Object Publishing Environment) is inspired by ZOPE. - -%package -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore-devel -Summary: Development files for the GNUstep database libraries -Group: Development/Libraries/Objective C -Requires: sope%{sope_major_version}%{sope_minor_version}-gdl1 -AutoReqProv: off - -%description -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore-devel -This package contains the header files for SOPE's GDLContentStore library. - -SOPE is a framework for developing web applications and services. The -name "SOPE" (SKYRiX Object Publishing Environment) is inspired by ZOPE. - -%package -n sope%{sope_major_version}%{sope_minor_version}-cards -Summary: SOPE versit parsing library for iCal and VCard formats -Group: Development/Libraries/Objective C -AutoReqProv: off - -%description -n sope%{sope_major_version}%{sope_minor_version}-cards -SOPE versit parsing library for iCal and VCard formats - -%package -n sope%{sope_major_version}%{sope_minor_version}-cards-devel -Summary: SOPE versit parsing library for iCal and VCard formats -Group: Development/Libraries/Objective C -Requires: sope%{sope_major_version}%{sope_minor_version}-cards -AutoReqProv: off - -%description -n sope%{sope_major_version}%{sope_minor_version}-cards-devel -SOPE versit parsing library for iCal and VCard formats - -%if %enable_openchange -%package openchange-backend -Summary: SOGo backend for OpenChange -Group: Productivity/Groupware -AutoReqProv: off - -%description openchange-backend -SOGo backend for OpenChange -%endif - -######################################## -%prep -rm -fr ${RPM_BUILD_ROOT} -%setup -q -n SOGo-%{sogo_version} - - -# small tweak to the python script for RHEL5 -# if hex(sys.hexversion) < 0x02060000 -%if %{python_sys_pyver} < 33947648 - sed -i 's!/usr/bin/env python!/usr/bin/env python2.6!' Scripts/openchange_user_cleanup -%endif - - -# ****************************** build ******************************** -%build -%if 0%{?el7} -. /usr/lib64/GNUstep/Makefiles/GNUstep.sh -%else -. /usr/share/GNUstep/Makefiles/GNUstep.sh -%endif -./configure %saml2_cfg_opts - -case %{_target_platform} in -ppc64-*) - cc="gcc -m64"; - ldflags="-m64";; -*) - cc="gcc"; - ldflags="";; -esac - -make CC="$cc" LDFLAGS="$ldflags" messages=yes - -# OpenChange -%if %{sogo_major_version} >= 2 -(cd OpenChange; \ - LD_LIBRARY_PATH=../SOPE/NGCards/obj:../SOPE/GDLContentStore/obj \ - make GNUSTEP_INSTALLATION_DOMAIN=SYSTEM ) -%endif - -# ****************************** install ****************************** -%install -QA_SKIP_BUILD_ROOT=1 -export QA_SKIP_BUILD_ROOT - -case %{_target_platform} in -ppc64-*) - cc="gcc -m64"; - ldflags="-m64";; -*) - cc="gcc"; - ldflags="";; -esac - -make DESTDIR=${RPM_BUILD_ROOT} \ - GNUSTEP_INSTALLATION_DOMAIN=SYSTEM \ - CC="$cc" LDFLAGS="$ldflags" \ - install -install -d ${RPM_BUILD_ROOT}/usr/lib/systemd/system/ -install -d ${RPM_BUILD_ROOT}/etc/cron.d -install -d ${RPM_BUILD_ROOT}/etc/cron.daily -install -d ${RPM_BUILD_ROOT}/etc/logrotate.d -install -d ${RPM_BUILD_ROOT}/etc/sysconfig -install -d ${RPM_BUILD_ROOT}/etc/httpd/conf.d -install -d ${RPM_BUILD_ROOT}/usr/sbin -install -d ${RPM_BUILD_ROOT}/var/lib/sogo -install -d ${RPM_BUILD_ROOT}/var/log/sogo -install -d ${RPM_BUILD_ROOT}/var/run/sogo -install -d ${RPM_BUILD_ROOT}/var/spool/sogo -install -d -m 750 -o %sogo_user -g %sogo_user ${RPM_BUILD_ROOT}/etc/sogo -install -m 640 -o %sogo_user -g %sogo_user Scripts/sogo.conf ${RPM_BUILD_ROOT}/etc/sogo/ -install -m 755 Scripts/openchange_user_cleanup ${RPM_BUILD_ROOT}/%{_sbindir} -cat Apache/SOGo.conf | sed -e "s@/lib/@/%{_lib}/@g" > ${RPM_BUILD_ROOT}/etc/httpd/conf.d/SOGo.conf -install -m 600 Scripts/sogo.cron ${RPM_BUILD_ROOT}/etc/cron.d/sogo -cp Scripts/tmpwatch ${RPM_BUILD_ROOT}/etc/cron.daily/sogo-tmpwatch -chmod 755 ${RPM_BUILD_ROOT}/etc/cron.daily/sogo-tmpwatch -cp Scripts/logrotate ${RPM_BUILD_ROOT}/etc/logrotate.d/sogo -cp Scripts/sogo-systemd-redhat ${RPM_BUILD_ROOT}/usr/lib/systemd/system/sogod.service -chmod 644 ${RPM_BUILD_ROOT}/usr/lib/systemd/system/sogod.service -cp Scripts/sogo-default ${RPM_BUILD_ROOT}/etc/sysconfig/sogo -rm -rf ${RPM_BUILD_ROOT}%{_bindir}/test_quick_extract - -# OpenChange -%if %{sogo_major_version} >= 2 -(cd OpenChange; \ - LD_LIBRARY_PATH=${RPM_BUILD_ROOT}%{_libdir} \ - make DESTDIR=${RPM_BUILD_ROOT} \ - GNUSTEP_INSTALLATION_DOMAIN=SYSTEM \ - CC="$cc" LDFLAGS="$ldflags" \ - install) -%endif - -# ActiveSync -(cd ActiveSync; \ - LD_LIBRARY_PATH=${RPM_BUILD_ROOT}%{_libdir} \ - make DESTDIR=${RPM_BUILD_ROOT} \ - GNUSTEP_INSTALLATION_DOMAIN=SYSTEM \ - CC="$cc" LDFLAGS="$ldflags" \ - install) - -# ****************************** clean ******************************** -%clean -rm -fr ${RPM_BUILD_ROOT} - -# ****************************** files ******************************** -%files -n sogo -%defattr(-,root,root,-) - -/etc/init.d/sogod -/etc/cron.daily/sogo-tmpwatch -%dir %attr(0700, %sogo_user, %sogo_user) %{_var}/lib/sogo -%dir %attr(0700, %sogo_user, %sogo_user) %{_var}/log/sogo -%dir %attr(0755, %sogo_user, %sogo_user) %{_var}/run/sogo -%dir %attr(0700, %sogo_user, %sogo_user) %{_var}/spool/sogo -%dir %attr(0750, root, %sogo_user) %{_sysconfdir}/sogo -%{_sbindir}/sogod -%{_sbindir}/openchange_user_cleanup -%{_libdir}/sogo/libSOGo.so* -%{_libdir}/sogo/libSOGoUI.so* -%{_libdir}/GNUstep/SOGo/AdministrationUI.SOGo -%{_libdir}/GNUstep/SOGo/Appointments.SOGo -%{_libdir}/GNUstep/SOGo/CommonUI.SOGo -%{_libdir}/GNUstep/SOGo/Contacts.SOGo -%{_libdir}/GNUstep/SOGo/ContactsUI.SOGo -%{_libdir}/GNUstep/SOGo/MailPartViewers.SOGo -%{_libdir}/GNUstep/SOGo/Mailer.SOGo -%{_libdir}/GNUstep/SOGo/MailerUI.SOGo -%{_libdir}/GNUstep/SOGo/MainUI.SOGo -%{_libdir}/GNUstep/SOGo/PreferencesUI.SOGo -%{_libdir}/GNUstep/SOGo/SchedulerUI.SOGo - -%{_libdir}/GNUstep/Frameworks/SOGo.framework/Resources -%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/%{sogo_major_version}/sogo/libSOGo.so* -%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/%{sogo_major_version}/Resources -%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/Current -%{_libdir}/GNUstep/SOGo/Templates -%{_libdir}/GNUstep/SOGo/WebServerResources -%{_libdir}/GNUstep/OCSTypeModels -%{_libdir}/GNUstep/WOxElemBuilders-* - -%config(noreplace) %attr(0640, root, %sogo_user) %{_sysconfdir}/sogo/sogo.conf -%config(noreplace) %{_sysconfdir}/logrotate.d/sogo -%config(noreplace) %{_sysconfdir}/cron.d/sogo -%config(noreplace) %{_sysconfdir}/httpd/conf.d/SOGo.conf -%config(noreplace) %{_sysconfdir}/sysconfig/sogo -%doc ChangeLog NEWS Scripts/*sh Scripts/updates.php Apache/SOGo-apple-ab.conf - -%files -n sogo-tool -%{_sbindir}/sogo-tool - -%files -n sogo-ealarms-notify -%{_sbindir}/sogo-ealarms-notify - -%files -n sogo-slapd-sockd -%{_sbindir}/sogo-slapd-sockd - -%files -n sogo-activesync -%{_libdir}/GNUstep/SOGo/ActiveSync.SOGo -%doc ActiveSync/LICENSE ActiveSync/README - -%files -n sogo-devel -%{_includedir}/SOGo -%{_includedir}/SOGoUI -%{_libdir}/sogo/libSOGo.so* -%{_libdir}/sogo/libSOGoUI.so* -%{_libdir}/GNUstep/Frameworks/SOGo.framework/Headers -%{_libdir}/GNUstep/Frameworks/SOGo.framework/sogo/libSOGo.so -%{_libdir}/GNUstep/Frameworks/SOGo.framework/sogo/SOGo -%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/%{sogo_major_version}/Headers -%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/%{sogo_major_version}/sogo/libSOGo.so* -%{_libdir}/GNUstep/Frameworks/SOGo.framework/Versions/%{sogo_major_version}/sogo/SOGo - -%files -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore -%defattr(-,root,root,-) -%{_libdir}/sogo/libGDLContentStore*.so* - -%files -n sope%{sope_major_version}%{sope_minor_version}-gdl1-contentstore-devel -%{_includedir}/GDLContentStore -%{_libdir}/sogo/libGDLContentStore*.so* - -%files -n sope%{sope_major_version}%{sope_minor_version}-cards -%{_libdir}/sogo/libNGCards.so* -%{_libdir}/GNUstep/SaxDrivers-* -%{_libdir}/GNUstep/SaxMappings -%{_libdir}/GNUstep/Libraries/Resources/NGCards - -%files -n sope%{sope_major_version}%{sope_minor_version}-cards-devel -%{_includedir}/NGCards -%{_libdir}/sogo/libNGCards.so* - -%if %enable_openchange -%files openchange-backend -%defattr(-,root,root,-) -%{_libdir}/GNUstep/SOGo/*.MAPIStore -%{_libdir}/mapistore_backends/* -%endif - -# **************************** pkgscripts ***************************** -%pre -if ! id %sogo_user >& /dev/null; then - /usr/sbin/useradd -d %{_var}/lib/sogo -c "SOGo daemon" -s /sbin/nologin -M -r %sogo_user -fi - -%post -# update timestamp on imgs,css,js to let apache know the files changed -find %{_libdir}/GNUstep/SOGo/WebServerResources -exec touch {} \; -systemctl enable sogod -systemctl start sogod > /dev/null 2>&1 - -%preun -if [ "$1" == "0" ] -then - systemctl disable sogod - systemctl stop sogod > /dev/null 2>&1 -fi - -%postun -if test "$1" = "0" -then - /usr/sbin/userdel %sogo_user - /usr/sbin/groupdel %sogo_user > /dev/null 2>&1 - /bin/rm -rf %{_var}/run/sogo - /bin/rm -rf %{_var}/spool/sogo - # not removing /var/lib/sogo to keep .GNUstepDefaults -fi - -# ********************************* changelog ************************* -%changelog -* Thu Mar 31 2015. Inverse inc. -- Change script start sogod for systemd - -* Wed Oct 8 2014 Inverse inc. -- fixed the library move to "sogo" app dir - -* Wed Jan 15 2014 Inverse inc. -- New package: sogo-activesync -- explicitly list all *.SOGo modules in sogo package -- added dependency on sogo = %version for sogo-tool - -* Thu Apr 17 2013 Inverse inc. -- Install openchange_user_cleanup in sbindir instead of doc - -* Wed Apr 10 2013 Inverse inc. -- use %sogo_user instead of 'sogo' -- install a sample sogo.conf in /etc/sogo - -* Tue Jan 22 2013 Inverse inc. -- Create the sogo user as a system user -- Use %attr() to set directory permissions instead of chown/chmod - -* Mon Nov 12 2012 Inverse inc. -- Add missing dependency on lasso and lasso-devel - -* Mon Nov 05 2012 Inverse inc. -- Disable saml2 on rhel5 - glib2 too old - -* Fri Nov 02 2012 Inverse inc. -- Enable saml2 - -* Tue Aug 28 2012 Inverse inc. -- Add openchange_cleanup.py and tweak it to work on RHEL5 - -* Tue Jul 31 2012 Inverse inc. -- treat logrotate file as a config file - -* Fri May 24 2012 Inverse inc. -- %post: restart sogo if it was running before rpm install - -* Fri Mar 16 2012 Inverse inc. -- %post: update timestamp on imgs,css,js to let apache know the files changed - -* Fri Feb 16 2012 Inverse inc. -- Use globbing to include all sql upgrade scripts instead of listing them all - -* Tue Jan 10 2012 Inverse inc. -- /etc/cron.d/sogo - -* Thu Oct 27 2011 Inverse inc. -- make build of sogo-openchange-backend conditional to sogo_version >= 2 - -* Fri Oct 14 2011 Inverse inc. -- adapted to gnustep-make 2.6 -- added sogo-openchange-backend - -* Tue Sep 28 2010 Inverse inc. -- removed "README" from documentation - -* Fri Aug 20 2010 Inverse inc. -- added sogo-ealarms-notify package - -* Tue Apr 06 2010 Inverse inc. -- added sogo-slapd-sockd package - -* Thu Jul 31 2008 Inverse inc. -- added dependencies on sopeXY-appserver, -core, -gdl1-contentstore and -ldap - -* Wed May 21 2008 Inverse inc. -- removed installation of template and resource files, since it is now done by the upstream package - -* Tue Oct 4 2007 Inverse inc. -- added package sope-gdl1-contentstore - -* Wed Jul 18 2007 Inverse inc. -- initial build From 94d546dc7a87ee65cfa0668da7bfd889e6155129 Mon Sep 17 00:00:00 2001 From: Ludovic Marcotte Date: Tue, 31 Mar 2015 13:42:59 -0400 Subject: [PATCH 09/19] (feat) added systemd startup script (PR#76) --- NEWS | 1 + 1 file changed, 1 insertion(+) diff --git a/NEWS b/NEWS index 708fc7f59..e402364d2 100644 --- a/NEWS +++ b/NEWS @@ -3,6 +3,7 @@ Enhancements - improved multipart handling using EAS + - added systemd startup script (PR#76) Bug fixes - now keep the BodyPreference for future EAS use and default to MIME if none set (#3146) From ab121e6c153208a9e18174d664645c52826ae9d2 Mon Sep 17 00:00:00 2001 From: Francis Lachapelle Date: Tue, 31 Mar 2015 15:19:53 -0400 Subject: [PATCH 10/19] [fix] Issues with freebusy in attendees editor --- NEWS | 1 + UI/WebServerResources/JavascriptAPIExtensions.js | 9 ++++----- UI/WebServerResources/UIxAttendeesEditor.js | 12 ++++++++++-- 3 files changed, 15 insertions(+), 7 deletions(-) diff --git a/NEWS b/NEWS index e402364d2..b9b1c6661 100644 --- a/NEWS +++ b/NEWS @@ -9,6 +9,7 @@ Bug fixes - now keep the BodyPreference for future EAS use and default to MIME if none set (#3146) - EAS reply fix when message/rfc822 parts are included in the original mail (#3153) - fix yet an other potential crash during freebusy lookups during timezone changes + - fix display of freebusy information in event attendees editor during timezone changes 2.2.17a (2015-03-15) -------------------- diff --git a/UI/WebServerResources/JavascriptAPIExtensions.js b/UI/WebServerResources/JavascriptAPIExtensions.js index 190a8e99b..0ee1b6b1e 100644 --- a/UI/WebServerResources/JavascriptAPIExtensions.js +++ b/UI/WebServerResources/JavascriptAPIExtensions.js @@ -130,7 +130,7 @@ Date.prototype.deltaDays = function(otherDate) { day1 = tmp; } - return Math.floor((day2 - day1) / 86400000); + return Math.round((day2 - day1) / 86400000); } Date.prototype.daysUpTo = function(otherDate) { @@ -152,7 +152,7 @@ Date.prototype.daysUpTo = function(otherDate) { // var day1 = day1Date.getTime(); // var day2 = day2Date.getTime(); - var nbrDays = Math.floor((day2 - day1) / 86400000) + 1; + var nbrDays = Math.round((day2 - day1) / 86400000) + 1; for (var i = 0; i < nbrDays; i++) { var newDate = new Date(); newDate.setTime(day1 + (i * 86400000)); @@ -217,9 +217,8 @@ Date.prototype.stringWithSeparator = function(separator) { }; Date.prototype.addDays = function(nbrDays) { - var milliSeconds = this.getTime(); - milliSeconds += 86400000 * Math.round(nbrDays); - this.setTime(milliSeconds); + var dat = new Date(this.valueOf()); + this.setDate(dat.getDate() + Math.round(nbrDays)); }; Date.prototype.earlierDate = function(otherDate) { diff --git a/UI/WebServerResources/UIxAttendeesEditor.js b/UI/WebServerResources/UIxAttendeesEditor.js index 7ca8e2874..be7a854bd 100644 --- a/UI/WebServerResources/UIxAttendeesEditor.js +++ b/UI/WebServerResources/UIxAttendeesEditor.js @@ -391,6 +391,12 @@ function redisplayEventSpans() { etHour++; } + if (isAllDay) { + addDays++; + stHour = stMinute = 0; + etHour = etMinute = 0; + } + if (stHour < displayStartHour) { stHour = displayStartHour; stMinute = 0; @@ -432,8 +438,10 @@ function redisplayEventSpans() { if (currentSpanNbr > 3) { currentSpanNbr = 0; currentCellNbr++; - currentCell = row.cells[currentCellNbr]; - spans = $(currentCell).childNodesWithTag("span"); + if (currentCellNbr < row.cells.length) { + currentCell = row.cells[currentCellNbr]; + spans = $(currentCell).childNodesWithTag("span"); + } } deltaSpans--; } From b2d7eb40c2d86b9c536477170eebe68716212b60 Mon Sep 17 00:00:00 2001 From: Ludovic Marcotte Date: Tue, 31 Mar 2015 16:13:52 -0400 Subject: [PATCH 11/19] (fix) fixed a potential EAS error with multiple email priority flags --- ActiveSync/SOGoMailObject+ActiveSync.m | 13 +++++++++++-- NEWS | 3 ++- 2 files changed, 13 insertions(+), 3 deletions(-) diff --git a/ActiveSync/SOGoMailObject+ActiveSync.m b/ActiveSync/SOGoMailObject+ActiveSync.m index d8aa6e0f9..1d74830c6 100644 --- a/ActiveSync/SOGoMailObject+ActiveSync.m +++ b/ActiveSync/SOGoMailObject+ActiveSync.m @@ -600,7 +600,11 @@ struct GlobalObjectId { // Importance v = 0x1; - p = [[self mailHeaders] objectForKey: @"x-priority"]; + value = [[self mailHeaders] objectForKey: @"x-priority"]; + if ([value isKindOfClass: [NSArray class]]) + p = [value lastObject]; + else + p = value; if (p) { @@ -611,7 +615,12 @@ struct GlobalObjectId { } else { - p = [[self mailHeaders] objectForKey: @"importance"]; + value = [[self mailHeaders] objectForKey: @"importance"]; + if ([value isKindOfClass: [NSArray class]]) + p = [value lastObject]; + else + p = value; + if ([p hasPrefix: @"High"]) v = 0x2; else if ([p hasPrefix: @"Low"]) v = 0x0; } diff --git a/NEWS b/NEWS index b9b1c6661..2a552a6f7 100644 --- a/NEWS +++ b/NEWS @@ -8,8 +8,9 @@ Enhancements Bug fixes - now keep the BodyPreference for future EAS use and default to MIME if none set (#3146) - EAS reply fix when message/rfc822 parts are included in the original mail (#3153) - - fix yet an other potential crash during freebusy lookups during timezone changes + - fixed yet an other potential crash during freebusy lookups during timezone changes - fix display of freebusy information in event attendees editor during timezone changes + - fixed a potential EAS error with multiple email priority flags 2.2.17a (2015-03-15) -------------------- From 9b320ec2a175f1db74a410b8a34767b4c28951e7 Mon Sep 17 00:00:00 2001 From: Ludovic Marcotte Date: Tue, 31 Mar 2015 16:17:21 -0400 Subject: [PATCH 12/19] Improvements over 491d7aaffcc2fc2b8acb468e6387501c2af376e4 --- ActiveSync/SOGoMailObject+ActiveSync.m | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/ActiveSync/SOGoMailObject+ActiveSync.m b/ActiveSync/SOGoMailObject+ActiveSync.m index 1d74830c6..15e3b1ca7 100644 --- a/ActiveSync/SOGoMailObject+ActiveSync.m +++ b/ActiveSync/SOGoMailObject+ActiveSync.m @@ -224,9 +224,17 @@ struct GlobalObjectId { while ((key = [e nextObject])) { - // don't use body parts from a nested body - e.g. body of type message/rfc822 - if (![key hasPrefix: @"1"]) + // Don't use body parts from nested bodies if not of type multipart/alternative. - e.g. body of type message/rfc822 + // Use only parts of level 0 or 1. + if ([key countOccurrencesOfString: @"."] > 1) continue; + else if ([key countOccurrencesOfString: @"."] == 1) + { + // Ignore nested parts if the container is not of type multipart/alternative. + part = [self lookupInfoForBodyPart: [[key componentsSeparatedByString: @"."] objectAtIndex:0]]; + if (!([[part valueForKey: @"type"] isEqualToString: @"multipart"] && [[part valueForKey: @"subtype"] isEqualToString: @"alternative"])) + continue; + } part = [self lookupInfoForBodyPart: key]; type = [part valueForKey: @"type"]; From 77917780c81310ab72cc294798a2574cf84d6544 Mon Sep 17 00:00:00 2001 From: Ludovic Marcotte Date: Wed, 1 Apr 2015 08:46:46 -0400 Subject: [PATCH 13/19] (fix) packaging issue on RHEL --- packaging/rhel/sogo.spec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packaging/rhel/sogo.spec b/packaging/rhel/sogo.spec index 33afa3f1a..02bf547ce 100644 --- a/packaging/rhel/sogo.spec +++ b/packaging/rhel/sogo.spec @@ -417,7 +417,7 @@ fi # ********************************* changelog ************************* %changelog -* Thu Mar 31 2015. Inverse inc. +* Thu Mar 31 2015 Inverse inc. - Change script start sogod for systemd * Wed Oct 8 2014 Inverse inc. From e2c3259b164d16c4ae4cbe4aa14914d071e9c80a Mon Sep 17 00:00:00 2001 From: Francis Lachapelle Date: Wed, 1 Apr 2015 20:10:52 -0400 Subject: [PATCH 14/19] [fix] Issues with freebusy in attendees editor --- UI/WebServerResources/JavascriptAPIExtensions.js | 6 +++--- UI/WebServerResources/UIxAttendeesEditor.js | 10 +++++----- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/UI/WebServerResources/JavascriptAPIExtensions.js b/UI/WebServerResources/JavascriptAPIExtensions.js index 0ee1b6b1e..245078268 100644 --- a/UI/WebServerResources/JavascriptAPIExtensions.js +++ b/UI/WebServerResources/JavascriptAPIExtensions.js @@ -119,7 +119,7 @@ Date.prototype.clone = function() { newDate.setTime(this.getTime()); return newDate; -} +}; Date.prototype.deltaDays = function(otherDate) { var day1 = this.getTime(); @@ -131,7 +131,7 @@ Date.prototype.deltaDays = function(otherDate) { } return Math.round((day2 - day1) / 86400000); -} +}; Date.prototype.daysUpTo = function(otherDate) { var days = new Array(); @@ -248,7 +248,7 @@ Date.prototype.beginOfDay = function() { beginOfDay.setMilliseconds(0); return beginOfDay; -} +}; Date.prototype.beginOfWeek = function() { var offset = firstDayOfWeek - this.getDay(); diff --git a/UI/WebServerResources/UIxAttendeesEditor.js b/UI/WebServerResources/UIxAttendeesEditor.js index be7a854bd..16d297425 100644 --- a/UI/WebServerResources/UIxAttendeesEditor.js +++ b/UI/WebServerResources/UIxAttendeesEditor.js @@ -905,7 +905,7 @@ _freeBusyCacheEntry.prototype = { var adjustedEd = ed.beginOfDay(); var nbrDays = adjustedSd.deltaDays(adjustedEd) + 1; var offsetEnd = offset + (nbrDays * 96); - if (Math.round(this.entries.length/96) >= nbrDays) { + if (Math.round((this.entries.length - offset)/96) >= nbrDays) { entries = this.entries.slice(offset, offsetEnd); } } @@ -942,7 +942,6 @@ _freeBusyCacheEntry.prototype = { // Period extends to after current end if (start.getTime() <= nextDate.getTime()) { start = nextDate.beginOfDay(); - start.addDays(1); } fetchDates.push({ start: start, end: end }); } @@ -960,7 +959,7 @@ _freeBusyCacheEntry.prototype = { if (this.startDate) { if (start.getTime() < this.startDate) { days = start.deltaDays(this.startDate); - if (entries.length == (days * 96)) { + if (Math.round(entries.length/96) == days) { // New period is just before previous period this.startDate = start; this.entries = entries.concat(this.entries); @@ -1131,7 +1130,7 @@ function displayFreeBusyForNode(input) { var rowIndex = input.parentNode.parentNode.sectionRowIndex; var row = $("freeBusyData").tBodies[0].rows[rowIndex]; var nodes = row.cells; - //log ("displayFreeBusyForNode index " + rowIndex + " (" + nodes.length + " cells)"); + //log ("displayFreeBusyForNode index " + rowIndex + " uid " + input.uid + " (" + nodes.length + " cells)"); if (input.uid) { if (!input.hasfreebusy) { // log("forcing draw of nodes"); @@ -1459,10 +1458,11 @@ function onTimeDateWidgetChange() { function prepareTableHeaders() { var startTimeDate = $("startTime_date"); var startDate = startTimeDate.inputAsDate(); + startDate.setHours(0, 0); var endTimeDate = $("endTime_date"); var endDate = endTimeDate.inputAsDate(); - endDate.setTime(endDate.getTime()); + endDate.setHours(0, 0); var rows = $("freeBusyHeader").rows; var days = startDate.daysUpTo(endDate); From 01857a9a47ae11561ab844a8759478f48ee607d3 Mon Sep 17 00:00:00 2001 From: Francis Lachapelle Date: Thu, 2 Apr 2015 11:53:03 -0400 Subject: [PATCH 15/19] [fix] Timezone of MS Exchange freebusy information --- NEWS | 3 ++- .../MSExchangeFreeBusySOAPRequest.m | 20 +++++++++++++++++-- 2 files changed, 20 insertions(+), 3 deletions(-) diff --git a/NEWS b/NEWS index 2a552a6f7..6c559e539 100644 --- a/NEWS +++ b/NEWS @@ -9,7 +9,8 @@ Bug fixes - now keep the BodyPreference for future EAS use and default to MIME if none set (#3146) - EAS reply fix when message/rfc822 parts are included in the original mail (#3153) - fixed yet an other potential crash during freebusy lookups during timezone changes - - fix display of freebusy information in event attendees editor during timezone changes + - fixed display of freebusy information in event attendees editor during timezone changes + - fixed timezone of MSExchange freebusy information - fixed a potential EAS error with multiple email priority flags 2.2.17a (2015-03-15) diff --git a/SoObjects/Appointments/MSExchangeFreeBusySOAPRequest.m b/SoObjects/Appointments/MSExchangeFreeBusySOAPRequest.m index 01c9e8aea..425178b36 100644 --- a/SoObjects/Appointments/MSExchangeFreeBusySOAPRequest.m +++ b/SoObjects/Appointments/MSExchangeFreeBusySOAPRequest.m @@ -70,11 +70,27 @@ to: (NSCalendarDate *) newEndDate { ASSIGN(address, newAddress); - ASSIGN(startDate, newStartDate); - ASSIGN(endDate, newEndDate); + + startDate = [NSCalendarDate dateWithYear: [newStartDate yearOfCommonEra] + month: [newStartDate monthOfYear] + day: [newStartDate dayOfMonth] + hour: [newStartDate hourOfDay] + minute: [newStartDate minuteOfHour] + second: [newStartDate secondOfMinute] + timeZone: [newStartDate timeZone]]; + endDate = [NSCalendarDate dateWithYear: [newEndDate yearOfCommonEra] + month: [newEndDate monthOfYear] + day: [newEndDate dayOfMonth] + hour: [newEndDate hourOfDay] + minute: [newEndDate minuteOfHour] + second: [newEndDate secondOfMinute] + timeZone: [newEndDate timeZone]]; [startDate setTimeZone: timeZone]; [endDate setTimeZone: timeZone]; + + [startDate retain]; + [endDate retain]; } - (NSString *) serverVersion From eae327ca191957ad956be7c750761c341ce599a9 Mon Sep 17 00:00:00 2001 From: Francis Lachapelle Date: Tue, 7 Apr 2015 08:27:30 -0400 Subject: [PATCH 16/19] [fix] Paragraph margins in HTML message Fixes #3163 --- NEWS | 1 + UI/WebServerResources/MailerUI.css | 1 - 2 files changed, 1 insertion(+), 1 deletion(-) diff --git a/NEWS b/NEWS index 6c559e539..4ee6daf1f 100644 --- a/NEWS +++ b/NEWS @@ -12,6 +12,7 @@ Bug fixes - fixed display of freebusy information in event attendees editor during timezone changes - fixed timezone of MSExchange freebusy information - fixed a potential EAS error with multiple email priority flags + - fixed paragraphs margins in HTML messages (#3163) 2.2.17a (2015-03-15) -------------------- diff --git a/UI/WebServerResources/MailerUI.css b/UI/WebServerResources/MailerUI.css index abd14f5c8..61c8750b2 100644 --- a/UI/WebServerResources/MailerUI.css +++ b/UI/WebServerResources/MailerUI.css @@ -510,7 +510,6 @@ DIV.mailer_htmlcontent P white-space: normal; font-family: sans-serif; font-size: inherit; - margin: 0px; padding: 0px; } From 755efa789bb2cfdc6f3c056266cbaa9575a91b4e Mon Sep 17 00:00:00 2001 From: Francis Lachapelle Date: Wed, 8 Apr 2015 12:07:28 -0400 Subject: [PATCH 17/19] [fix] initial loading of inbox uids and headers --- NEWS | 1 + UI/WebServerResources/MailerUI.js | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/NEWS b/NEWS index 4ee6daf1f..59fe4397a 100644 --- a/NEWS +++ b/NEWS @@ -13,6 +13,7 @@ Bug fixes - fixed timezone of MSExchange freebusy information - fixed a potential EAS error with multiple email priority flags - fixed paragraphs margins in HTML messages (#3163) + - fixed regression when loading the inbox for the first time 2.2.17a (2015-03-15) -------------------- diff --git a/UI/WebServerResources/MailerUI.js b/UI/WebServerResources/MailerUI.js index 995a11f9c..1941ed32b 100644 --- a/UI/WebServerResources/MailerUI.js +++ b/UI/WebServerResources/MailerUI.js @@ -916,10 +916,11 @@ function openMailbox(mailbox, reload) { dataSource.init(inboxData['uids'], inboxData['threaded'], inboxData['headers'], inboxData['quotas']); inboxData = null; // invalidate this initial lookup } - else + else { // Fetch UIDs and headers from server var content = Object.toJSON(urlParams); dataSource.load(content); + } // Cache data source Mailer.dataSources.set(key, dataSource); // Update unseen count From 1e4596ca3a42bc1e3c64d4c0d075fb7ea09336be Mon Sep 17 00:00:00 2001 From: Ludovic Marcotte Date: Wed, 8 Apr 2015 14:20:33 -0400 Subject: [PATCH 18/19] (fix) fixed serialization of PreventInvitationsWhitelist --- NEWS | 1 + UI/PreferencesUI/UIxPreferences.m | 14 ++++++++++---- 2 files changed, 11 insertions(+), 4 deletions(-) diff --git a/NEWS b/NEWS index 59fe4397a..d888d1a07 100644 --- a/NEWS +++ b/NEWS @@ -14,6 +14,7 @@ Bug fixes - fixed a potential EAS error with multiple email priority flags - fixed paragraphs margins in HTML messages (#3163) - fixed regression when loading the inbox for the first time + - fixed serialization of the PreventInvitationsWhitelist settings 2.2.17a (2015-03-15) -------------------- diff --git a/UI/PreferencesUI/UIxPreferences.m b/UI/PreferencesUI/UIxPreferences.m index 6e54bc043..9f55e4166 100644 --- a/UI/PreferencesUI/UIxPreferences.m +++ b/UI/PreferencesUI/UIxPreferences.m @@ -640,15 +640,21 @@ static NSArray *reminderValues = nil; return [userDefaults busyOffHours]; } -- (NSArray *) whiteList +- (NSString *) whiteList { SOGoUserSettings *us; NSMutableDictionary *moduleSettings; - NSArray *whiteList; + id whiteList; us = [user userSettings]; moduleSettings = [us objectForKey: @"Calendar"]; - whiteList = [moduleSettings objectForKey:@"PreventInvitationsWhitelist"]; + whiteList = [moduleSettings objectForKey: @"PreventInvitationsWhitelist"]; + + if (whiteList && [whiteList isKindOfClass: [NSDictionary class]]) + { + whiteList = [whiteList jsonRepresentation]; + } + return whiteList; } @@ -659,7 +665,7 @@ static NSArray *reminderValues = nil; us = [user userSettings]; moduleSettings = [us objectForKey: @"Calendar"]; - [moduleSettings setObject: whiteListString forKey: @"PreventInvitationsWhitelist"]; + [moduleSettings setObject: [whiteListString objectFromJSONString] forKey: @"PreventInvitationsWhitelist"]; [us synchronize]; } From cdc74e498448d701dc8ea9998542effc13d5cb0c Mon Sep 17 00:00:00 2001 From: Francis Lachapelle Date: Thu, 9 Apr 2015 09:06:19 -0400 Subject: [PATCH 19/19] Update translations --- NEWS | 1 + .../Localizable.strings | 2 +- .../Localizable.strings | 2 +- .../Localizable.strings | 16 ++-- .../Localizable.strings | 90 +++++++++---------- .../Localizable.strings | 2 +- .../Localizable.strings | 10 +-- .../NorwegianBokmal.lproj/Localizable.strings | 2 +- .../Localizable.strings | 6 +- .../Localizable.strings | 42 +++++---- .../Dutch.lproj/Localizable.strings | 4 + .../NorwegianBokmal.lproj/Localizable.strings | 10 ++- .../Polish.lproj/Localizable.strings | 4 + .../Russian.lproj/Localizable.strings | 7 ++ .../SpanishSpain.lproj/Localizable.strings | 4 + .../Localizable.strings | 22 ++--- .../English.lproj/Localizable.strings | 3 +- 17 files changed, 130 insertions(+), 97 deletions(-) diff --git a/NEWS b/NEWS index d888d1a07..08b83e687 100644 --- a/NEWS +++ b/NEWS @@ -4,6 +4,7 @@ Enhancements - improved multipart handling using EAS - added systemd startup script (PR#76) + - updated Brazilian (Portuguese), Dutch, Norwegian (Bokmal), Polish, Russian, and Spanish (Spain) translations Bug fixes - now keep the BodyPreference for future EAS use and default to MIME if none set (#3146) diff --git a/SoObjects/Appointments/BrazilianPortuguese.lproj/Localizable.strings b/SoObjects/Appointments/BrazilianPortuguese.lproj/Localizable.strings index f6117f8ef..5fcb33090 100644 --- a/SoObjects/Appointments/BrazilianPortuguese.lproj/Localizable.strings +++ b/SoObjects/Appointments/BrazilianPortuguese.lproj/Localizable.strings @@ -56,7 +56,7 @@ vtodo_class2 = "(Tarefa Confidencial)"; "%{Attendee} %{SentByText}has accepted your event invitation." = "%{Attendee} %{SentByText}foi aceitado seu convite ao evento."; "%{Attendee} %{SentByText}has declined your event invitation." -= "%{Attendee} %{SentByText}foi declinado seu convite ao evento."; += "%{Attendee} %{SentByText}recusou seu convite para o evento."; "%{Attendee} %{SentByText}has delegated the invitation to %{Delegate}." = "%{Attendee} %{SentByText} delegou o convite para %{Delegate}."; "%{Attendee} %{SentByText}has not yet decided upon your event invitation." diff --git a/SoObjects/Contacts/BrazilianPortuguese.lproj/Localizable.strings b/SoObjects/Contacts/BrazilianPortuguese.lproj/Localizable.strings index 8923eae93..9b2176e92 100644 --- a/SoObjects/Contacts/BrazilianPortuguese.lproj/Localizable.strings +++ b/SoObjects/Contacts/BrazilianPortuguese.lproj/Localizable.strings @@ -1,2 +1,2 @@ -"Personal Address Book" = "Livro de Endereços Pessoais"; +"Personal Address Book" = "Livro de Endereço Pessoal"; "Collected Address Book" = "Catálogos Coletados"; diff --git a/UI/Common/BrazilianPortuguese.lproj/Localizable.strings b/UI/Common/BrazilianPortuguese.lproj/Localizable.strings index dabc4b454..0e6c1db6e 100644 --- a/UI/Common/BrazilianPortuguese.lproj/Localizable.strings +++ b/UI/Common/BrazilianPortuguese.lproj/Localizable.strings @@ -94,7 +94,7 @@ "OK" = "OK"; "Cancel" = "Cancelar"; "Yes" = "Sim"; -"No" = "No"; +"No" = "Não"; /* alarms */ "Reminder:" = "Lembrete:"; @@ -109,10 +109,10 @@ "To Do" = "Tarefa"; "Later" = "Adiar"; -"a2_Sunday" = "Do"; -"a2_Monday" = "Se"; -"a2_Tuesday" = "Te"; -"a2_Wednesday" = "Qu"; -"a2_Thursday" = "Qu"; -"a2_Friday" = "Se"; -"a2_Saturday" = "Sa"; +"a2_Sunday" = "Dom"; +"a2_Monday" = "Seg"; +"a2_Tuesday" = "Ter"; +"a2_Wednesday" = "Qua"; +"a2_Thursday" = "Qui"; +"a2_Friday" = "Sex"; +"a2_Saturday" = "Sab"; diff --git a/UI/Contacts/BrazilianPortuguese.lproj/Localizable.strings b/UI/Contacts/BrazilianPortuguese.lproj/Localizable.strings index 934456c1c..4a09eae65 100644 --- a/UI/Contacts/BrazilianPortuguese.lproj/Localizable.strings +++ b/UI/Contacts/BrazilianPortuguese.lproj/Localizable.strings @@ -1,20 +1,20 @@ /* this file is in UTF-8 format! */ -"Contact" = "Contact"; -"Address" = "Address"; -"Photos" = "Photos"; -"Other" = "Other"; +"Contact" = "Contato"; +"Address" = "Catálogo"; +"Photos" = "Fotos"; +"Other" = "Outros"; -"Address Books" = "Addressbooks"; +"Address Books" = "Catálogo de Endereços"; "Addressbook" = "Catálogo"; -"Addresses" = "Contato"; +"Addresses" = "Endereços"; "Update" = "Atualizar"; "Cancel" = "Cancelar"; "Common" = "Comum"; "Contact editor" = "Editor de Contatos"; "Contact viewer" = "Visualizador de Contatos"; "Email" = "Email"; -"Screen Name" = "Nome Apresentação"; +"Screen Name" = "Nome de Exibição"; "Extended" = "Extendido"; "Fax" = "Fax"; "Firstname" = "Primeiro Nome"; @@ -32,16 +32,16 @@ "Postal" = "CEP"; "Save" = "Salvar"; "Internet" = "Internet"; -"Unit" = "Setor"; +"Unit" = "Unidade"; "delete" = "apagar"; "edit" = "editar"; "invalidemailwarn" = "O email informado é inválido"; "new" = "novo"; "Preferred Phone" = "Telefone Preferencial"; -"Move To" = "Move To"; -"Copy To" = "Copy To"; -"Add to:" = "Add to:"; +"Move To" = "Mover para"; +"Copy To" = "Copiar para"; +"Add to:" = "Adicionar em:"; /* Tooltips */ @@ -50,14 +50,14 @@ "Edit the selected card" = "Edita o contato selecionado"; "Send a mail message" = "Envia uma mensagem de email"; "Delete selected card or address book" = "Apaga o contato ou catálogo selecionado"; -"Reload all contacts" = "Reload all contacts"; +"Reload all contacts" = "Recarregar todos os contatos"; "htmlMailFormat_UNKNOWN" = "Desconhecido"; "htmlMailFormat_FALSE" = "Texto Puro"; "htmlMailFormat_TRUE" = "HTML"; "Name or Email" = "Nome ou Email"; -"Category" = "Category"; +"Category" = "Categoria"; "Personal Addressbook" = "Catálogo Pessoal"; "Search in Addressbook" = "Localizar no Catálogo"; @@ -76,15 +76,15 @@ "No possible subscription" = "Sem possibilidades de inscrição"; "Preferred" = "Preferido"; -"Display:" = "Display:"; +"Display:" = "Exibição:"; "Display Name:" = "Exibir Nome:"; "Email:" = "Endereço de Email:"; -"Additional Email:" = "Additional Email:"; +"Additional Email:" = "Email Adicional:"; -"Phone Number:" = "Phone Number:"; -"Prefers to receive messages formatted as:" = "Prefers to receive messages formatted as:"; -"Screen Name:" = "Screen Name:"; -"Categories:" = "Categories:"; +"Phone Number:" = "Telefone:"; +"Prefers to receive messages formatted as:" = "Prefere receber mensagens formatadas como:"; +"Screen Name:" = "Nome de Exibição:"; +"Categories:" = "Categorias:"; "First:" = "Primeiro Nome:"; "Last:" = "Último Nome:"; @@ -98,22 +98,22 @@ "Pager:" = "Pager:"; /* categories */ -"contacts_category_labels" = "Colleague, Competitor, Customer, Friend, Family, Business Partner, Provider, Press, VIP"; -"Categories" = "Categories"; -"New category" = "New category"; +"contacts_category_labels" = "Colega, Concorrente, Cliente, Amigo, Família, Parceiro de Negócios, Provedor, Press, VIP"; +"Categories" = "Categorias"; +"New category" = "Nova categoria"; /* adresses */ "Title:" = "Título:"; "Service:" = "Serviço:"; "Company:" = "Empresa:"; -"Department:" = "Department:"; -"Organization:" = "Organization:"; +"Department:" = "Departamento"; +"Organization:" = "Organização"; "Address:" = "Endereço:"; "City:" = "Cidade:"; "State_Province:" = "Estado:"; "ZIP_Postal Code:" = "CEP:"; "Country:" = "País:"; -"Web Page:" = "Web Page:"; +"Web Page:" = "Página Web:"; "Work" = "Comercial"; "Other Infos" = "Outras Informações"; @@ -125,7 +125,7 @@ "Freebusy URL:" = "URL Livre/Ocupado:"; "Add as..." = "Adicionar como..."; -"Recipient" = "Recipient"; +"Recipient" = "Destinatário"; "Carbon Copy" = "Cópia Carbono"; "Blind Carbon Copy" = "Cópia Carbono Oculta"; @@ -158,8 +158,8 @@ "Access rights to" = "Direitos de acesso para"; "For user" = "Para usuário"; -"Any Authenticated User" = "Any Authenticated User"; -"Public Access" = "Public Access"; +"Any Authenticated User" = "Qualquer Usuário Autenticado"; +"Public Access" = "Acesso Público"; "This person can add cards to this addressbook." = "Essa pessoa pode adicionar contatos ao meu catálogo."; @@ -185,25 +185,25 @@ "Unknown Destination Folder" = "O catálogo de destino selecionado não existe."; /* Lists */ -"List details" = "List details"; -"List name:" = "List name:"; -"List nickname:" = "List nickname:"; -"List description:" = "List description:"; -"Members" = "Members"; -"Contacts" = "Contacts"; -"Add" = "Add"; -"Lists can't be moved or copied." = "Lists can't be moved or copied."; -"Export" = "Export"; -"Export Address Book..." = "Export Address Book..."; +"List details" = "Detalhes da lista"; +"List name:" = "Lista nome:"; +"List nickname:" = "Lista Apelido:"; +"List description:" = "Lista descrição:"; +"Members" = "Membros"; +"Contacts" = "Contatos"; +"Add" = "Adicionar"; +"Lists can't be moved or copied." = "As listas não podem ser movidos ou copiados."; +"Export" = "Exportar"; +"Export Address Book..." = "Exportar Catálogo de Endereço..."; "View Raw Source" = "Visualizar Fonte"; -"Import Cards" = "Import Cards"; -"Select a vCard or LDIF file." = "Select a vCard or LDIF file."; -"Upload" = "Upload"; +"Import Cards" = "Importar cartões"; +"Select a vCard or LDIF file." = "Selecione um arquivo vCard ou LDIF."; +"Upload" = "Carregar"; "Uploading" = "Carregando"; -"Done" = "Done"; -"An error occured while importing contacts." = "An error occured while importing contacts."; -"No card was imported." = "No card was imported."; -"A total of %{0} cards were imported in the addressbook." = "A total of %{0} cards were imported in the addressbook."; +"Done" = "Pronto"; +"An error occured while importing contacts." = "Ocorreu um erro ao importar contatos."; +"No card was imported." = "Nenhum cartão foi importado."; +"A total of %{0} cards were imported in the addressbook." = "Um total de %{0} cartões foram importados no catálogo de endereços."; "Reload" = "Atualizar"; diff --git a/UI/MailPartViewers/BrazilianPortuguese.lproj/Localizable.strings b/UI/MailPartViewers/BrazilianPortuguese.lproj/Localizable.strings index d038b316d..94b9e6bec 100644 --- a/UI/MailPartViewers/BrazilianPortuguese.lproj/Localizable.strings +++ b/UI/MailPartViewers/BrazilianPortuguese.lproj/Localizable.strings @@ -10,7 +10,7 @@ you_are_an_attendee = "você é um participante"; add_info_text = "As solicitações iMIP 'ADD' ainda não são suportadas pelo SOGo."; publish_info_text = "O solicitante lhe informa sobre um evento anexo."; cancel_info_text = "Seu convite ou evento foi cancelado."; -request_info_no_attendee = "está propondo um reunião aos participantes. Você está recebendo este email como uma notificação, você não está agendado como um particiopante."; +request_info_no_attendee = "está propondo uma reunião aos participantes. Você está recebendo este email como uma notificação, você não está agendado como um particiopante."; Appointment = "Apontamento"; "Status Update" = "Status da Atualização"; was = "foi"; diff --git a/UI/MailerUI/BrazilianPortuguese.lproj/Localizable.strings b/UI/MailerUI/BrazilianPortuguese.lproj/Localizable.strings index b07718473..92af97fe0 100644 --- a/UI/MailerUI/BrazilianPortuguese.lproj/Localizable.strings +++ b/UI/MailerUI/BrazilianPortuguese.lproj/Localizable.strings @@ -26,7 +26,7 @@ /* Tooltips */ "Send this message now" = "Envia esta mensagem agora"; -"Select a recipient from an Address Book" = "Seleciona um destinatário de a partir de um Catálogo"; +"Select a recipient from an Address Book" = "Seleciona um destinatário de catálogo de endereços"; "Include an attachment" = "Inclui um anexo"; "Save this message" = "Salva esta mensagem"; "Get new messages" = "Receber novas mensagens"; @@ -95,7 +95,7 @@ "Subject" = "Assunto"; "To" = "Para"; "Cc" = "Cc"; -"Bcc" = "Bcc"; +"Bcc" = "Cco"; "Reply-To" = "Responder-Para"; "Add address" = "Adicionar endereço"; "Body" = "Corpo"; @@ -109,7 +109,7 @@ "to" = "Para"; "cc" = "Cc"; -"bcc" = "Bcc"; +"bcc" = "Cco"; "Edit Draft..." = "Editar Rascunho..."; "Load Images" = "Carregar Imagens"; @@ -180,7 +180,7 @@ /* Address Popup menu */ "Add to Address Book..." = "Adicionar ao Catálogo..."; -"Compose Mail To" = "Escrever Mensagem Parana"; +"Compose Mail To" = "Escrever Mensagem Para"; "Create Filter From Message..." = "Criar Filtro Da Mensagem..."; /* Image Popup menu */ @@ -261,7 +261,7 @@ "Operation failed" = "Falha na Operação"; "Quota" = "Quota:"; -"quotasFormat" = "%{0}% usedo em %{1} MB"; +"quotasFormat" = "%{0}% usado em %{1} MB"; "Please select a message." = "Por favor, selecione uma mensagem."; "Please select a message to print." = "Por favor, selecione a mensagem para imprimir."; diff --git a/UI/MailerUI/NorwegianBokmal.lproj/Localizable.strings b/UI/MailerUI/NorwegianBokmal.lproj/Localizable.strings index c389d4c13..e2f6937d9 100644 --- a/UI/MailerUI/NorwegianBokmal.lproj/Localizable.strings +++ b/UI/MailerUI/NorwegianBokmal.lproj/Localizable.strings @@ -17,7 +17,7 @@ "Send" = "Send"; "Contacts" = "Kontakter"; -"Attach" = "Vedlegg ved"; +"Attach" = "Vedlegg"; "Save" = "Lagre"; "Options" = "Innstillinger"; "Close" = "Lukk"; diff --git a/UI/MainUI/BrazilianPortuguese.lproj/Localizable.strings b/UI/MainUI/BrazilianPortuguese.lproj/Localizable.strings index 4bc1a21ca..0f8f74599 100644 --- a/UI/MainUI/BrazilianPortuguese.lproj/Localizable.strings +++ b/UI/MainUI/BrazilianPortuguese.lproj/Localizable.strings @@ -10,7 +10,7 @@ "Connect" = "Conectar"; "Wrong username or password." = "Usuário ou Senha Inválido."; -"cookiesNotEnabled" = "Você não pode logar por a opção cookies está desabilitada. Por favor, habilite os cookies nas configurações de seu navegador e tente novamente."; +"cookiesNotEnabled" = "Você não pode logar porque a opção cookies está desabilitada. Por favor, habilite os cookies nas configurações de seu navegador e tente novamente."; "browserNotCompatible" = "Foi detectado que a atual versão de seu navegador não é suportado neste site. Recomentamos que use o Firefox. Clique no link abaixo para baixar a versão atual deste navegador."; "alternativeBrowsers" = "Alternativamente, você pode usar os seguinte navegadores compatíveis"; @@ -44,7 +44,7 @@ "Welsh" = "Cymraeg"; "About" = "Sobre"; -"AboutBox" = "Developed by Inverse, SOGo is a fully-featured groupware server with a focus on scalability and simplicity.

⏎ \nSOGo provides a rich AJAX-based Web interface and supports multiple native clients through the use of standard protocols such as CalDAV and CardDAV.

⏎ \nSOGo is distributed under the GNU GPL version 2 or later and parts are distributed under the GNU LGPL version 2. This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law.

⏎ \nSee this page for various support options."; +"AboutBox" = "Desenvolvido por Inverse, Sogo é um servidor de groupware cheio de recursos com foco em escalabilidade e simplicidade.\nSogo fornece uma interface Web baseada em AJAX ricos e suporta vários clientes nativos através da utilização de protocolos padrão como CalDAV e CardDAV.\nSogo é distribuído sob a GNU GPL versão 2 ou posterior e as partes são distribuídos sob a GNU LGPL versão 2. Este é um software livre: você é livre para mudar e redistribuí-lo. Não há NENHUMA GARANTIA, até o limite permitido por lei.\nVeja desta página para várias opções de suporte."; "Your account was locked due to too many failed attempts." = "Sua conta foi bloqueada devido a muitas tentativas fracassadas."; "Your account was locked due to an expired password." = "Sua conta foi bloqueada devido a uma senha expirada."; @@ -67,7 +67,7 @@ "Password change failed - Insufficient password quality" = "Alteração da senha falhou - Senha muito fraca"; "Password change failed - Password is too short" = "Alteração da senha falhou - Senha muito curta"; "Password change failed - Password is too young" = "Alteração da senha falhou - Senha usada recentemente"; -"Password change failed - Password is in history" = "Password is too young - Senha está no histórico"; +"Password change failed - Password is in history" = "Alteração de senha falhou - Password está no histórico"; "Unhandled policy error: %{0}" = "Política de erro não tratada: %{0}"; "Unhandled error response" = "Erro de resposta não tratado"; "Password change is not supported." = "Alteração da senha não suportada."; diff --git a/UI/PreferencesUI/BrazilianPortuguese.lproj/Localizable.strings b/UI/PreferencesUI/BrazilianPortuguese.lproj/Localizable.strings index 01dc12d01..77db2492b 100644 --- a/UI/PreferencesUI/BrazilianPortuguese.lproj/Localizable.strings +++ b/UI/PreferencesUI/BrazilianPortuguese.lproj/Localizable.strings @@ -23,12 +23,13 @@ /* vacation (auto-reply) */ "Enable vacation auto reply" = "Habilitar auto resposta de férias"; -"Auto reply message :" = "AutoResponder somente uma vez a cada remetente com o seguinte texto :"; +"Auto reply message :" = "Auto Responder somente uma vez a cada remetente com o seguinte texto:"; "Email addresses (separated by commas) :" = "Endereço de e-mail (separado por vírgulas):"; "Add default email addresses" = "Adicionar endereço de e-mail padrão"; "Days between responses :" = "Dias entre respostas:"; "Do not send responses to mailing lists" = "Não envie respostas para lista de e-mails"; "Disable auto reply on" = "Desativar resposta automática em"; +"Always send vacation message response" = "Sempre enviar resposta de mensagem de férias"; "Please specify your message and your email addresses for which you want to enable auto reply." = "Favor especificar a sua mensagem e seus endereços de e-mail para o qual você deseja ativar resposta automática."; "Your vacation message must not end with a single dot on a line." = "Sua mensagem de férias não deve terminar com um ponto único em uma linha."; @@ -40,9 +41,12 @@ "Keep a copy" = "Manter uma cópia"; "Please specify an address to which you want to forward your messages." = "Favor especificar um endereço para o qual você deseja encaminhar suas mensagens."; +"You are not allowed to forward your messages to an external email address." = "Você não tem permissão para transmitir a sua mensagem para um endereço de e-mail externo."; +"You are not allowed to forward your messages to an internal email address." = "Você não tem permissão para transmitir a sua mensagem para um endereço de e-mail interno."; + /* d & t */ -"Current Time Zone :" = "Fuso Horário :"; +"Current Time Zone :" = "Fuso Horário:"; "Short Date Format :" = "Formato da Data (Curto) :"; "Long Date Format :" = "Formato da Data (Longo) :"; "Time Format :" = "Formato da Hora :"; @@ -170,7 +174,7 @@ "User Name:" = "Nome do Usuário:"; "Password:" = "Senha:"; -"Full Name:" = "Nome Compelto:"; +"Full Name:" = "Nome Completo:"; "Email:" = "E-mail:"; "Reply To Email:" = "Responder para o Email:"; "Signature:" = "Assinatura:"; @@ -207,7 +211,7 @@ "Mail" = "Correio"; "Last" = "Último usado"; "Default Module :" = "Módulo Padrão:"; -"SOGo Version :" = "Versão SOGo:"; +"SOGo Version :" = "Versão do SOGo:"; "Language :" = "Idioma :"; "choose" = "Escolha ..."; @@ -283,7 +287,7 @@ "Header" = "Cabeçalho"; "Body" = "Corpo"; "Flag the message with:" = "Marcar a mensagem com:"; -"Discard the message" = "Discate a mensagem"; +"Discard the message" = "Descarte a mensagem"; "File the message in:" = "Arquivo da mensagem em:"; "Keep the message" = "Manter a mensagem"; "Forward the message to:" = "Encaminhar a mensagem para:"; @@ -293,7 +297,7 @@ "is under" = "abaixo"; "is over" = "acima"; -"is" = "is"; +"is" = "é igual"; "is not" = "não é"; "contains" = "contem"; "does not contain" = "não contem"; @@ -307,19 +311,19 @@ "Answered" = "Respondido"; "Flagged" = "Marcado"; "Junk" = "Lixo"; -"Not Junk" = "Não é Lixo"; +"Not Junk" = "Não é Lixo Eletrônico"; /* Password policy */ "The password was changed successfully." = "Senha alterada com sucesso."; -"Password must not be empty." = "Le mot de passe ne doit pas être vide."; -"The passwords do not match. Please try again." = "Les mots de passe ne sont pas identiques. Essayez de nouveau."; -"Password change failed" = "Échec au changement"; -"Password change failed - Permission denied" = "Échec au changement - mauvaises permissions"; -"Password change failed - Insufficient password quality" = "Échec au changement - qualité insuffisante"; -"Password change failed - Password is too short" = "Échec au changement - mot de passe trop court"; -"Password change failed - Password is too young" = "Échec au changement - mot de passe trop récent"; -"Password change failed - Password is in history" = "Échec au changement - mot de passe dans l'historique"; -"Unhandled policy error: %{0}" = "Erreur inconnue pour le ppolicy: %{0}"; -"Unhandled error response" = "Erreur inconnue"; -"Password change is not supported." = "Changement de mot de passe non-supporté."; -"Unhandled HTTP error code: %{0}" = "Code HTTP non-géré: %{0}"; +"Password must not be empty." = "A Senha não pode ser vazia."; +"The passwords do not match. Please try again." = "As senhas não coincidem. Por favor, tente novamente."; +"Password change failed" = "Alteração de senha falhou"; +"Password change failed - Permission denied" = "Alteração de senha falhou - Permissão Negada"; +"Password change failed - Insufficient password quality" = "Alteração de senha falhou pois não atende os requisitos minímos"; +"Password change failed - Password is too short" = "Alteração de senha falhou - Senha muito curta"; +"Password change failed - Password is too young" = "Alteração de senha falhou - Senha alterada recentemente"; +"Password change failed - Password is in history" = "Alteração de senha falhou - A Senha já foi utilizada"; +"Unhandled policy error: %{0}" = "Erro de política não tratada: %{0}"; +"Unhandled error response" = "Resposta de erro não tratada"; +"Password change is not supported." = "Troca de senha não suportada"; +"Unhandled HTTP error code: %{0}" = "Código de erro HTTP não tratada: %{0}"; diff --git a/UI/PreferencesUI/Dutch.lproj/Localizable.strings b/UI/PreferencesUI/Dutch.lproj/Localizable.strings index f4fe086f4..89a6ad964 100644 --- a/UI/PreferencesUI/Dutch.lproj/Localizable.strings +++ b/UI/PreferencesUI/Dutch.lproj/Localizable.strings @@ -29,6 +29,7 @@ "Days between responses :" = "Dagen tussen reacties:"; "Do not send responses to mailing lists" = "Geen reacties naar maillinglijsten sturen"; "Disable auto reply on" = "Automatisch bericht bij afwezigheid uitschakelen op"; +"Always send vacation message response" = "Afwezigheidsbericht altijd versturen"; "Please specify your message and your email addresses for which you want to enable auto reply." = "Geeft u alstublieft de tekst van het automatische bericht bij afwezigheid op en de e-mailadressen waarvoor het moet worden geactiveerd."; "Your vacation message must not end with a single dot on a line." = "Uw automatisch bericht bij afwezigheid mag niet eindigen met een enkele punt op een regel."; @@ -40,6 +41,9 @@ "Keep a copy" = "Kopie bewaren"; "Please specify an address to which you want to forward your messages." = "Alstublieft het e-mailadres waarnaar u de berichten wilt laten doorsturen aangeven."; +"You are not allowed to forward your messages to an external email address." = "Email naar een extern emailadres doorsturen is niet toegestaan"; +"You are not allowed to forward your messages to an internal email address." = "Email naar een intern emailadres doorsturen is niet toegestaan"; + /* d & t */ "Current Time Zone :" = "Huidige tijdzone:"; diff --git a/UI/PreferencesUI/NorwegianBokmal.lproj/Localizable.strings b/UI/PreferencesUI/NorwegianBokmal.lproj/Localizable.strings index 17be0b3fa..c1f59838d 100644 --- a/UI/PreferencesUI/NorwegianBokmal.lproj/Localizable.strings +++ b/UI/PreferencesUI/NorwegianBokmal.lproj/Localizable.strings @@ -12,6 +12,7 @@ "Forward" = "Videresend"; "Password" = "Passord"; "Categories" = "Kategorier"; +"Appointments invitations" = "Avtale varslinger"; "Name" = "Navn"; "Color" = "Farge"; "Add" = "Legg til"; @@ -28,6 +29,7 @@ "Days between responses :" = "Dager mellom svar:"; "Do not send responses to mailing lists" = "Ikke send svar til e-postlister"; "Disable auto reply on" = "Skru av auto-svar"; +"Always send vacation message response" = "Alltid send ferie melding"; "Please specify your message and your email addresses for which you want to enable auto reply." = "Skriv melding og angi din e-postadresse som du vil aktivere auto-svar for."; "Your vacation message must not end with a single dot on a line." = "Fraværsmeldingen kan ikke slutte med ett ensomt punktum på en linje. "; @@ -39,6 +41,9 @@ "Keep a copy" = "Behold en kopi"; "Please specify an address to which you want to forward your messages." = "Angi adressen du vil videresende dine meldinger til."; +"You are not allowed to forward your messages to an external email address." = "Du har ikke lov til å videresende mail til en ekstern e-mail addresse."; +"You are not allowed to forward your messages to an internal email address." = "Du har ikke love til å videresende mail til en ekstern e-mail addresse."; + /* d & t */ "Current Time Zone :" = "Gjeldende tidssone:"; @@ -137,7 +142,7 @@ "Forward messages:" = "Videresend meldinger:"; "messageforward_inline" = "Innsatt"; -"messageforward_attached" = "Vedlegg"; +"messageforward_attached" = "Som Vedlegg"; "When replying to a message:" = "Ved svar på melding: "; "replyplacement_above" = "Start svaret ovenfor"; @@ -152,6 +157,9 @@ "displayremoteinlineimages_never" = "Aldri"; "displayremoteinlineimages_always" = "Alltid"; +"Auto save every" = "Lagre automatisk"; +"minutes" = "minutter"; + /* Contact */ "Personal Address Book" = "Personlig addressebok"; "Collected Address Book" = "Samlet addressebok"; diff --git a/UI/PreferencesUI/Polish.lproj/Localizable.strings b/UI/PreferencesUI/Polish.lproj/Localizable.strings index 9936e5a4c..e432f9182 100644 --- a/UI/PreferencesUI/Polish.lproj/Localizable.strings +++ b/UI/PreferencesUI/Polish.lproj/Localizable.strings @@ -29,6 +29,7 @@ "Days between responses :" = "Dni pomiędzy odpowiedziami :"; "Do not send responses to mailing lists" = "Nie wysyłaj odpowiedzi do grup pocztowych"; "Disable auto reply on" = "Zablokuj autoodpowiedź w"; +"Always send vacation message response" = "Zawsze wysyłaj autoodpowiedź"; "Please specify your message and your email addresses for which you want to enable auto reply." = "Podaj treść wiadomości i twoje adresy e-mail, dla których chcesz włączyć autoodpowiedź."; "Your vacation message must not end with a single dot on a line." = "Twoja wiadomość nie może kończyć się kropką w pustej linii."; @@ -40,6 +41,9 @@ "Keep a copy" = "Zatrzymaj kopię"; "Please specify an address to which you want to forward your messages." = "Podaj adres, na który chcesz przekazywać wiadomości."; +"You are not allowed to forward your messages to an external email address." = "Nie masz uprawnień do przesyłania dalej swoich wiadomości na zewnętrzny adres e-mail."; +"You are not allowed to forward your messages to an internal email address." = "Nie masz uprawnień do przesyłania dalej swoich wiadomości na wewnętrzny adres e-mail."; + /* d & t */ "Current Time Zone :" = "Bieżąca strefa czasowa :"; diff --git a/UI/PreferencesUI/Russian.lproj/Localizable.strings b/UI/PreferencesUI/Russian.lproj/Localizable.strings index 0dc61be59..59dc0c09e 100644 --- a/UI/PreferencesUI/Russian.lproj/Localizable.strings +++ b/UI/PreferencesUI/Russian.lproj/Localizable.strings @@ -29,6 +29,7 @@ "Days between responses :" = "Дни между ответами :"; "Do not send responses to mailing lists" = "Не отправлять ответы на почтовые списки рассылки"; "Disable auto reply on" = "Запрет автоответа включен"; +"Always send vacation message response" = "Всегда отправлять ответное сообщение об отпуске"; "Please specify your message and your email addresses for which you want to enable auto reply." = "Пожалуйста, укажите Ваше сообщение и адреса электронной почты для которых Вы хотите включить автоматический ответ."; "Your vacation message must not end with a single dot on a line." = "Ваше сообщение о верменном отсутсвии не должно оканчиваться строкой с одиночной точкой."; @@ -40,6 +41,9 @@ "Keep a copy" = "Оставлять копию"; "Please specify an address to which you want to forward your messages." = "Пожалуйста укажите адрес, на который вы хотите переадресовать ваши сообщения."; +"You are not allowed to forward your messages to an external email address." = "Вы не можете пересылать свои сообщения на внешний адрес электронной почты."; +"You are not allowed to forward your messages to an internal email address." = "Вы не можете пересылать свои сообщения на внутренний адрес электронной почты."; + /* d & t */ "Current Time Zone :" = "Текущая временная зона :"; @@ -153,6 +157,9 @@ "displayremoteinlineimages_never" = "Никогда"; "displayremoteinlineimages_always" = "Всегда"; +"Auto save every" = "Автосохранение каждые"; +"minutes" = "минут"; + /* Contact */ "Personal Address Book" = "Личная адресная книга"; "Collected Address Book" = "Собранные адреса"; diff --git a/UI/PreferencesUI/SpanishSpain.lproj/Localizable.strings b/UI/PreferencesUI/SpanishSpain.lproj/Localizable.strings index 7a5eb414a..55d72d435 100644 --- a/UI/PreferencesUI/SpanishSpain.lproj/Localizable.strings +++ b/UI/PreferencesUI/SpanishSpain.lproj/Localizable.strings @@ -29,6 +29,7 @@ "Days between responses :" = "Dias entre respuestas :"; "Do not send responses to mailing lists" = "No enviar respuestas a las listas de distribución"; "Disable auto reply on" = "Desactivar respuesta automatica"; +"Always send vacation message response" = "Siempre enviar mensaje de vacaciones"; "Please specify your message and your email addresses for which you want to enable auto reply." = "Por favor, especificar el mensaje y la dirección de correo para aquellos a los que quiere habilitar la respuesta automática."; "Your vacation message must not end with a single dot on a line." = "El mensaje de vacaciones no puede finalizarse con un único punto en una linea."; @@ -40,6 +41,9 @@ "Keep a copy" = "Guardar una copia"; "Please specify an address to which you want to forward your messages." = "Por favor, especificar una dirección para aquellos mensajes que quiere desviar."; +"You are not allowed to forward your messages to an external email address." = "No esta autorizado a reenviar sus mensajes a una dirección de correo externa."; +"You are not allowed to forward your messages to an internal email address." = "No esta autorizado a reenviar sus mensajes a una dirección de correo interna."; + /* d & t */ "Current Time Zone :" = "Zona horaria actual :"; diff --git a/UI/Scheduler/BrazilianPortuguese.lproj/Localizable.strings b/UI/Scheduler/BrazilianPortuguese.lproj/Localizable.strings index 3c5891e81..b3686c62f 100644 --- a/UI/Scheduler/BrazilianPortuguese.lproj/Localizable.strings +++ b/UI/Scheduler/BrazilianPortuguese.lproj/Localizable.strings @@ -7,7 +7,7 @@ "Edit this event or task" = "Editar este evento ou tarefa"; "Print the current calendar view" = "Imprimir a visualização do calendário atual"; "Delete this event or task" = "Apagar este evento ou tarefa"; -"Go to today" = "Vai para hoje"; +"Go to today" = "Ir para Hoje"; "Switch to day view" = "Visualizar Dia"; "Switch to week view" = "Visualizar Semana"; "Switch to month view" = "Visualizar Mês"; @@ -129,7 +129,7 @@ "Update" = "Atualizar"; "Cancel" = "Cancelar"; "show_rejected_apts" = "Exibir apontamentos rejeitados"; -"hide_rejected_apts" = "Ocultar apontamentos rejeitados"; +"hide_rejected_apts" = "Ocultar compromissos rejeitados"; /* Schedule */ @@ -144,7 +144,7 @@ "decline" = "Declinar"; "more attendees" = "Mais Participantes"; "Hide already accepted and rejected appointments" = "Ocultar apontamentos já aceitos e rejeitados"; -"Show already accepted and rejected appointments" = "Exibir apontamentos já aceitos e rejeitados"; +"Show already accepted and rejected appointments" = "Exibir compromissos já aceitos e rejeitados"; /* Print view */ @@ -163,10 +163,10 @@ /* Appointments */ -"Appointment viewer" = "Visualizador de Apontamentos"; -"Appointment editor" = "Editor de Apontamento"; -"Appointment proposal" = "Apontamento Proposto"; -"Appointment on" = "Apontamento em"; +"Appointment viewer" = "Visualizador de Compromissos"; +"Appointment editor" = "Editor de Compromisso"; +"Appointment proposal" = "Compromisso Proposto"; +"Appointment on" = "Compromisso em"; "Start:" = "Inicio:"; "End:" = "Fim:"; "Due Date:" = "Data:"; @@ -210,7 +210,7 @@ "Private" = "Privado"; /* text used in overviews and tooltips */ "empty title" = "Título Vazio"; -"private appointment" = "Apontamento privado"; +"private appointment" = "Compromisso privado"; "Change..." = "Alterar..."; @@ -331,7 +331,7 @@ "cycle_of" = "de"; "No end date" = "Sem data final"; "Create" = "Criar"; -"appointment(s)" = "apontamento(s)"; +"appointment(s)" = "compromisso(s)"; "Repeat until" = "Repetir até"; "First" = "Primeiro"; @@ -429,7 +429,7 @@ validate_endbeforestart = "A data que você informou ocorre antes da data ini /* menu */ "New Event..." = "Novo Evento..."; -"New Task..." = "Neva Tarefa..."; +"New Task..." = "Nova Tarefa"; "Edit Selected Event..." = "Editar o Evento Selecionado..."; "Delete Selected Event" = "Apagar o Evento Selecionado"; "Select All" = "Selecionar Tudo"; @@ -471,7 +471,7 @@ validate_endbeforestart = "A data que você informou ocorre antes da data ini "Work days only" = "Somente dias de trabalho"; "The whole day" = "O dia inteiro"; "Between" = "Entre"; -"and" = "and"; +"and" = "e"; "A time conflict exists with one or more attendees.\nWould you like to keep the current settings anyway?" = "Existe um conflito de tempo com um ou mais participantes.\nGostaria de manter as configurações atuais?"; diff --git a/UI/Scheduler/English.lproj/Localizable.strings b/UI/Scheduler/English.lproj/Localizable.strings index 321198ea8..4bb62c42b 100644 --- a/UI/Scheduler/English.lproj/Localizable.strings +++ b/UI/Scheduler/English.lproj/Localizable.strings @@ -325,9 +325,11 @@ "Week(s)" = "Week(s)"; "On" = "On"; "Month(s)" = "Month(s)"; +/* [Event recurrence editor] Ex: _The_ first Sunday */ "The" = "The"; "Recur on day(s)" = "Recur on day(s)"; "Year(s)" = "Year(s)"; +/* [Event recurrence editor] Ex: Every first Sunday _of_ April */ "cycle_of" = "of"; "No end date" = "No end date"; "Create" = "Create"; @@ -548,7 +550,6 @@ vtodo_class2 = "(Confidential task)"; "EventCopyError" = "The copy failed. Please try to copy to a difference calendar."; "Please select at least one calendar" = "Please select at least one calendar"; - "Open Task..." = "Open Task..."; "Mark Completed" = "Mark Completed"; "Delete Task" = "Delete Task";