aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorstuconnolly <stuart02@gmail.com>2012-09-06 11:00:21 +0000
committerstuconnolly <stuart02@gmail.com>2012-09-06 11:00:21 +0000
commit9b71e97f74c4d09a5fed11f28c084ee87fccf321 (patch)
treee3ebfd761819bf7d39df4087118461536731fe94
parent71e2c109a958b6663192948298b60fdba869b93a (diff)
downloadsequelpro-9b71e97f74c4d09a5fed11f28c084ee87fccf321.tar.gz
sequelpro-9b71e97f74c4d09a5fed11f28c084ee87fccf321.tar.bz2
sequelpro-9b71e97f74c4d09a5fed11f28c084ee87fccf321.zip
Add date/time handling.
-rw-r--r--Frameworks/PostgresKit/Source/FLXPostgresConnectionTypeHandling.m4
-rw-r--r--Frameworks/PostgresKit/Source/FLXPostgresTypeDateTimeHandler.h43
-rw-r--r--Frameworks/PostgresKit/Source/FLXPostgresTypeDateTimeHandler.m190
3 files changed, 187 insertions, 50 deletions
diff --git a/Frameworks/PostgresKit/Source/FLXPostgresConnectionTypeHandling.m b/Frameworks/PostgresKit/Source/FLXPostgresConnectionTypeHandling.m
index bd46e788..483519cf 100644
--- a/Frameworks/PostgresKit/Source/FLXPostgresConnectionTypeHandling.m
+++ b/Frameworks/PostgresKit/Source/FLXPostgresConnectionTypeHandling.m
@@ -22,6 +22,7 @@
#import "FLXPostgresConnectionTypeHandling.h"
#import "FLXPostgresTypeStringHandler.h"
#import "FLXPostgresTypeNumberHandler.h"
+#import "FLXPostgresTypeDateTimeHandler.h"
#import "FLXPostgresException.h"
@implementation FLXPostgresConnection (FLXPostgresConnectionTypeHandling)
@@ -38,7 +39,8 @@
}
[self registerTypeHandler:[FLXPostgresTypeStringHandler class]];
- [self registerTypeHandler:[FLXPostgresTypeNumberHandler class]];
+ [self registerTypeHandler:[FLXPostgresTypeNumberHandler class]];
+ [self registerTypeHandler:[FLXPostgresTypeDateTimeHandler class]];
}
/**
diff --git a/Frameworks/PostgresKit/Source/FLXPostgresTypeDateTimeHandler.h b/Frameworks/PostgresKit/Source/FLXPostgresTypeDateTimeHandler.h
index 154d364f..b83eba76 100644
--- a/Frameworks/PostgresKit/Source/FLXPostgresTypeDateTimeHandler.h
+++ b/Frameworks/PostgresKit/Source/FLXPostgresTypeDateTimeHandler.h
@@ -4,32 +4,29 @@
// FLXPostgresTypeDateTimeHandler.h
// PostgresKit
//
-// Created by Stuart Connolly (stuconnolly.com) on September 1, 2012.
-// Copyright (c) 2012 Stuart Connolly. All rights reserved.
+// Copyright (c) 2008-2009 David Thorpe, djt@mutablelogic.com
//
-// Permission is hereby granted, free of charge, to any person
-// obtaining a copy of this software and associated documentation
-// files (the "Software"), to deal in the Software without
-// restriction, including without limitation the rights to use,
-// copy, modify, merge, publish, distribute, sublicense, and/or sell
-// copies of the Software, and to permit persons to whom the
-// Software is furnished to do so, subject to the following
-// conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
-// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
-// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
-// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
-// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
-// OTHER DEALINGS IN THE SOFTWARE.
+// Forked by the Sequel Pro Team on July 22, 2012.
+//
+// Licensed under the Apache License, Version 2.0 (the "License"); you may not
+// use this file except in compliance with the License. You may obtain a copy of
+// the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+// License for the specific language governing permissions and limitations under
+// the License.
+
+@class FLXPostgresTypeNumberHandler;
#import "FLXPostgresTypeHandler.h"
-@interface FLXPostgresTypeDateTimeHandler : FLXPostgresTypeHandler <FLXPostgresTypeHandlerProtocol>
+@interface FLXPostgresTypeDateTimeHandler : FLXPostgresTypeHandler <FLXPostgresTypeHandlerProtocol>
+{
+ FLXPostgresTypeNumberHandler *_numberHandler;
+}
@end
diff --git a/Frameworks/PostgresKit/Source/FLXPostgresTypeDateTimeHandler.m b/Frameworks/PostgresKit/Source/FLXPostgresTypeDateTimeHandler.m
index 761e9e17..8f8ace87 100644
--- a/Frameworks/PostgresKit/Source/FLXPostgresTypeDateTimeHandler.m
+++ b/Frameworks/PostgresKit/Source/FLXPostgresTypeDateTimeHandler.m
@@ -4,42 +4,52 @@
// FLXPostgresTypeDateTimeHandler.m
// PostgresKit
//
-// Created by Stuart Connolly (stuconnolly.com) on September 1, 2012.
-// Copyright (c) 2012 Stuart Connolly. All rights reserved.
+// Copyright (c) 2008-2009 David Thorpe, djt@mutablelogic.com
//
-// Permission is hereby granted, free of charge, to any person
-// obtaining a copy of this software and associated documentation
-// files (the "Software"), to deal in the Software without
-// restriction, including without limitation the rights to use,
-// copy, modify, merge, publish, distribute, sublicense, and/or sell
-// copies of the Software, and to permit persons to whom the
-// Software is furnished to do so, subject to the following
-// conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
-// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
-// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
-// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
-// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
-// OTHER DEALINGS IN THE SOFTWARE.
+// Forked by the Sequel Pro Team on July 22, 2012.
+//
+// Licensed under the Apache License, Version 2.0 (the "License"); you may not
+// use this file except in compliance with the License. You may obtain a copy of
+// the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+// License for the specific language governing permissions and limitations under
+// the License.
#import "FLXPostgresTypeDateTimeHandler.h"
+#import "FLXPostgresTypeNumberHandler.h"
+#import "FLXPostgresConnectionParameters.h"
#import "FLXPostgresConnection.h"
+#import "FLXPostgresConnectionTypeHandling.h"
+
+// Microseconds per second
+#define USECS_PER_SEC 1000000
static FLXPostgresOid FLXPostgresTypeDateTimeTypes[] =
-{
- FLXPostgresOidAbsTime,
+{
FLXPostgresOidDate,
FLXPostgresOidTime,
FLXPostgresOidTimeTZ,
+ FLXPostgresOidAbsTime,
+ FLXPostgresOidTimestamp,
+ FLXPostgresOidTimestampTZ,
0
};
+@interface FLXPostgresTypeDateTimeHandler ()
+
+- (NSDate *)_postgresEpochDate;
+- (NSDate *)_dateFromBytes:(const void *)bytes length:(NSUInteger)length;
+- (NSDate *)_timeFromBytes:(const void *)bytes length:(NSUInteger)length;
+- (NSDate *)_timestampFromBytes:(const void *)bytes length:(NSUInteger)length;
+- (NSDate *)_dateByAddingComponents:(NSDateComponents *)components toDate:(NSDate *)date;
+
+@end
+
@implementation FLXPostgresTypeDateTimeHandler
#pragma mark -
@@ -71,8 +81,24 @@ static FLXPostgresOid FLXPostgresTypeDateTimeTypes[] =
{
if (!bytes || !type) return nil;
- // TODO: Imeplement me!
- return nil;
+ if (!_numberHandler) {
+ _numberHandler = (FLXPostgresTypeNumberHandler *)[_connection typeHandlerForClass:[NSNumber class]];
+ }
+
+ switch (type)
+ {
+ case FLXPostgresOidDate:
+ return [self _dateFromBytes:bytes length:length];
+ case FLXPostgresOidTime:
+ case FLXPostgresOidTimeTZ:
+ case FLXPostgresOidAbsTime:
+ return [self _timeFromBytes:bytes length:length];
+ case FLXPostgresOidTimestamp:
+ case FLXPostgresOidTimestampTZ:
+ return [self _timestampFromBytes:bytes length:length];
+ default:
+ return nil;
+ }
}
- (NSString *)quotedStringFromObject:(id)object
@@ -83,4 +109,116 @@ static FLXPostgresOid FLXPostgresTypeDateTimeTypes[] =
return nil;
}
+#pragma mark -
+#pragma mark Private API
+
+/**
+ * Returns the internal expoch date used by Postgres.
+ *
+ * @return The epoch date as an NSDate.
+ */
+- (NSDate *)_postgresEpochDate
+{
+ NSDateComponents *components = [[NSDateComponents alloc] init];
+
+ [components setDay:1];
+ [components setMonth:1];
+ [components setYear:2000];
+
+ NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
+
+ NSDate *date = [gregorian dateFromComponents:components];
+
+ [components release];
+ [gregorian release];
+
+ return date;
+}
+
+/**
+ * Converts the supplied bytes representing a date to an NSDate instance.
+ *
+ * @param bytes The bytes to convert.
+ * @param length The number of bytes.
+ *
+ * @return The NSDate representation.
+ */
+- (NSDate *)_dateFromBytes:(const void *)bytes length:(NSUInteger)length
+{
+ NSDateComponents *components = [[NSDateComponents alloc] init];
+
+ [components setDay:[[_numberHandler integerObjectFromBytes:bytes length:length] integerValue]];
+
+ NSDate *date = [self _dateByAddingComponents:components toDate:[self _postgresEpochDate]];
+
+ [components release];
+
+ return date;
+}
+
+/**
+ * Converts the supplied bytes representing the time to an NSDate instance.
+ *
+ * @param bytes The bytes to convert.
+ * @param length The number of bytes.
+ *
+ * @return The NSDate representation.
+ */
+- (NSDate *)_timeFromBytes:(const void *)bytes length:(NSUInteger)length
+{
+ NSNumber *time = [_numberHandler integerObjectFromBytes:bytes length:length];
+
+ return [NSDate dateWithTimeIntervalSince1970:(NSTimeInterval)[time doubleValue]];
+}
+
+/**
+ * Converts the supplied bytes representing a timestamp to an NSDate instance.
+ *
+ * @param bytes The bytes to convert.
+ * @param length The number of bytes.
+ *
+ * @return The NSDate representation.
+ */
+- (NSDate *)_timestampFromBytes:(const void *)bytes length:(NSUInteger)length
+{
+ NSDate *date = nil;
+ NSUInteger seconds = 0;
+
+ if ([[[_connection parameters] valueForParameter:FLXPostgresParameterIntegerDateTimes] boolValue]) {
+ seconds = ([[_numberHandler integerObjectFromBytes:bytes length:length] doubleValue] / (double)USECS_PER_SEC);
+ }
+ else {
+ seconds = [_numberHandler float64FromBytes:bytes];
+ }
+
+ NSDateComponents *components = [[NSDateComponents alloc] init];
+
+ [components setSecond:seconds];
+
+ date = [self _dateByAddingComponents:components toDate:[self _postgresEpochDate]];
+
+ [components release];
+
+ return date;
+}
+
+/**
+ * Returns the result of adding the supplied components to the supplied date.
+ *
+ * @param components The date components to add.
+ * @param date The date to add the components to.
+ *
+ * @return The result of the addition to the date.
+ */
+- (NSDate *)_dateByAddingComponents:(NSDateComponents *)components toDate:(NSDate *)date
+{
+ NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
+
+ NSDate *newDate = [gregorian dateByAddingComponents:components toDate:date options:0];
+
+ [gregorian release];
+
+ return newDate;
+}
+
@end