diff --git a/DXFeedFramework.xcodeproj/project.pbxproj b/DXFeedFramework.xcodeproj/project.pbxproj index e38579b47..dae5e85b2 100644 --- a/DXFeedFramework.xcodeproj/project.pbxproj +++ b/DXFeedFramework.xcodeproj/project.pbxproj @@ -213,7 +213,6 @@ 648BD56B2AC4576F004A3A95 /* HelpTool.swift in Sources */ = {isa = PBXBuildFile; fileRef = 648BD56A2AC4576F004A3A95 /* HelpTool.swift */; }; 648BD56D2AC56A04004A3A95 /* SubscriptionUtils.swift in Sources */ = {isa = PBXBuildFile; fileRef = 648BD56C2AC56A04004A3A95 /* SubscriptionUtils.swift */; }; 648BD56F2AC582AB004A3A95 /* DateTimeParserTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = 648BD56E2AC582AB004A3A95 /* DateTimeParserTest.swift */; }; - 648BD5712AC583AC004A3A95 /* TimeFormat.swift in Sources */ = {isa = PBXBuildFile; fileRef = 648BD5702AC583AC004A3A95 /* TimeFormat.swift */; }; 648E98AA2AAF625800BFD219 /* IIndexedEvent+Ext.swift in Sources */ = {isa = PBXBuildFile; fileRef = 648E98A92AAF625800BFD219 /* IIndexedEvent+Ext.swift */; }; 649282E72AD54919008F0F04 /* ScheduleUtils.swift in Sources */ = {isa = PBXBuildFile; fileRef = 649282E62AD54919008F0F04 /* ScheduleUtils.swift */; }; 649282E82AD54919008F0F04 /* ScheduleUtils.swift in Sources */ = {isa = PBXBuildFile; fileRef = 649282E62AD54919008F0F04 /* ScheduleUtils.swift */; }; @@ -685,7 +684,6 @@ 648BD56A2AC4576F004A3A95 /* HelpTool.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HelpTool.swift; sourceTree = ""; }; 648BD56C2AC56A04004A3A95 /* SubscriptionUtils.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SubscriptionUtils.swift; sourceTree = ""; }; 648BD56E2AC582AB004A3A95 /* DateTimeParserTest.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DateTimeParserTest.swift; sourceTree = ""; }; - 648BD5702AC583AC004A3A95 /* TimeFormat.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TimeFormat.swift; sourceTree = ""; }; 648E98A92AAF625800BFD219 /* IIndexedEvent+Ext.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "IIndexedEvent+Ext.swift"; sourceTree = ""; }; 649282E62AD54919008F0F04 /* ScheduleUtils.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ScheduleUtils.swift; sourceTree = ""; }; 649282E92AD55323008F0F04 /* IpfConnect.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IpfConnect.swift; sourceTree = ""; }; @@ -1154,7 +1152,6 @@ 64C771F12A94A224009868C2 /* Character+Ext.swift */, 64C772002A975102009868C2 /* Reference+Util.swift */, 6464074E2A9F62D4006FF769 /* Date+Ext.swift */, - 648BD5702AC583AC004A3A95 /* TimeFormat.swift */, 64A42F3A2B07A7A3001C3ACC /* SymbolParser.swift */, ); path = Utils; @@ -2327,7 +2324,6 @@ 640C3FD62A6179E300555161 /* CandleAlignment.swift in Sources */, 640C3FCC2A616B6200555161 /* ArgumentException.swift in Sources */, 64B436442AB88EA40003919E /* NativeDay.swift in Sources */, - 648BD5712AC583AC004A3A95 /* TimeFormat.swift in Sources */, 642BE4C42A2E1AFF0052340A /* Quote.swift in Sources */, 64656F602A1B9EC2006A0B19 /* EnumUtil.swift in Sources */, 64A42F492B0B9683001C3ACC /* NativeTimeFormat.swift in Sources */, diff --git a/DXFeedFramework/Api/Osub/TimeSeriesSubscriptionSymbol.swift b/DXFeedFramework/Api/Osub/TimeSeriesSubscriptionSymbol.swift index b0cfcad3a..63c3e59f6 100644 --- a/DXFeedFramework/Api/Osub/TimeSeriesSubscriptionSymbol.swift +++ b/DXFeedFramework/Api/Osub/TimeSeriesSubscriptionSymbol.swift @@ -53,7 +53,7 @@ public class TimeSeriesSubscriptionSymbol: GenericIndexedEventSubscriptionSymbol /// Custom symbol has to return string representation. public override var stringValue: String { - return "\(symbol){fromTime=\(TimeUtil.toLocalDateString(millis: fromTime))}" + return "\(symbol){fromTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: fromTime)) ?? "")}" } } diff --git a/DXFeedFramework/Events/Market/Candles/Candle.swift b/DXFeedFramework/Events/Market/Candles/Candle.swift index 63084fb9a..103df04ac 100644 --- a/DXFeedFramework/Events/Market/Candles/Candle.swift +++ b/DXFeedFramework/Events/Market/Candles/Candle.swift @@ -136,9 +136,9 @@ extension Candle { func baseFieldsToString() -> String { return """ \(eventSymbol), \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ eventFlags=\(eventFlags.toHexString()), \ -time=\(TimeUtil.toLocalDateString(millis: time)), \ +time=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: time)) ?? ""), \ sequence=\(getSequence()), \ count=\(count), \ open=\(open), \ diff --git a/DXFeedFramework/Events/Market/Extra/OrderBase.swift b/DXFeedFramework/Events/Market/Extra/OrderBase.swift index aedb62812..b397c4314 100644 --- a/DXFeedFramework/Events/Market/Extra/OrderBase.swift +++ b/DXFeedFramework/Events/Market/Extra/OrderBase.swift @@ -285,18 +285,19 @@ extension OrderBase { /// Returns string representation of this candle fields. func baseFieldsToString() -> String { + return """ \(eventSymbol), \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ source=\(eventSource.name), \ eventFlags=\(eventFlags.toHexString()), \ index=\(index.toHexString()), \ -time=\(TimeUtil.toLocalDateString(millis: time)), \ +time=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: time)) ?? ""), \ sequence=\(getSequence()), \ timeNanoPart=\(timeNanoPart), \ action=\(action), \ -actionTime=\(TimeUtil.toLocalDateString(millis: actionTime)), \ +actionTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: actionTime)) ?? ""), \ orderId=\(orderId), \ auxOrderId=\(auxOrderId), \ price=\(price), \ diff --git a/DXFeedFramework/Events/Market/Extra/TradeBase.swift b/DXFeedFramework/Events/Market/Extra/TradeBase.swift index 99ff38da2..3734d6391 100644 --- a/DXFeedFramework/Events/Market/Extra/TradeBase.swift +++ b/DXFeedFramework/Events/Market/Extra/TradeBase.swift @@ -172,8 +172,8 @@ extension TradeBase { func baseFieldsToString() -> String { return """ \(eventSymbol), \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ -time=\(TimeUtil.toLocalDateString(millis: time)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ +time=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: time)) ?? ""), \ timeNanoPart=\(timeNanoPart), \ sequence=\(self.getSequence()), \ exchange=\(StringUtil.encodeChar(char: exchangeCode)), \ diff --git a/DXFeedFramework/Events/Market/Greeks.swift b/DXFeedFramework/Events/Market/Greeks.swift index bfe677852..79f9e987f 100644 --- a/DXFeedFramework/Events/Market/Greeks.swift +++ b/DXFeedFramework/Events/Market/Greeks.swift @@ -119,9 +119,9 @@ extension Greeks { public func toString() -> String { return """ Greeks{\(eventSymbol), \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ eventFlags=\(eventFlags.toHexString()), \ -time=\(TimeUtil.toLocalDateString(millis: time)), \ +time=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: time)) ?? ""), \ sequence=\(self.getSequence()), \ price=\(price), \ volatility=\(volatility), \ diff --git a/DXFeedFramework/Events/Market/OptionSale.swift b/DXFeedFramework/Events/Market/OptionSale.swift index 2bfb42c05..435fc5bc7 100644 --- a/DXFeedFramework/Events/Market/OptionSale.swift +++ b/DXFeedFramework/Events/Market/OptionSale.swift @@ -238,10 +238,10 @@ extension OptionSale { public func toString() -> String { return """ OptionSale{\(eventSymbol), \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ eventFlags=\(eventFlags.toHexString()), \ index=\(index.toHexString()), \ -time=\(TimeUtil.toLocalDateString(millis: time)), \ +time=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: time)) ?? ""), \ timeNanoPart=\(timeNanoPart), \ sequence=\(getSequence()), \ exchange=\(StringUtil.encodeChar(char: exchangeCode)), \ diff --git a/DXFeedFramework/Events/Market/Profile.swift b/DXFeedFramework/Events/Market/Profile.swift index 2eaff0e39..494fa77f6 100644 --- a/DXFeedFramework/Events/Market/Profile.swift +++ b/DXFeedFramework/Events/Market/Profile.swift @@ -143,13 +143,13 @@ extension Profile { func baseFieldsToString() -> String { return """ \(eventSymbol), \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ description='\(descriptionStr ?? "null")', \ SSR=\(shortSaleRestriction), \ status=\(tradingStatus), \ statusReason='\(statusReason ?? "null")', \ -haltStartTime=\(TimeUtil.toLocalDateStringWithoutMillis(millis: haltStartTime)), \ -haltEndTime=\(TimeUtil.toLocalDateStringWithoutMillis(millis: haltEndTime)), \ +haltStartTime=\((try? DXTimeFormat.defaultTimeFormat?.format(value: haltStartTime)) ?? ""), \ +haltEndTime=\((try? DXTimeFormat.defaultTimeFormat?.format(value: haltEndTime)) ?? ""), \ highLimitPrice=\(highLimitPrice), \ lowLimitPrice=\(lowLimitPrice), \ high52WeekPrice=\(high52WeekPrice), \ diff --git a/DXFeedFramework/Events/Market/Quote.swift b/DXFeedFramework/Events/Market/Quote.swift index 07d4b139b..7f3aeefa2 100644 --- a/DXFeedFramework/Events/Market/Quote.swift +++ b/DXFeedFramework/Events/Market/Quote.swift @@ -129,15 +129,15 @@ extension Quote { func baseFieldsToString() -> String { return """ \(eventSymbol), \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ -time=\(TimeUtil.toLocalDateString(millis: time)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ +time=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: time)) ?? ""), \ timeNanoPart=\(timeNanoPart), \ sequence=\(getSequence()), \ -bidTime=\(TimeUtil.toLocalDateStringWithoutMillis(millis: bidTime)), \ +bidTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: bidTime)) ?? ""), \ bidExchange=\(StringUtil.encodeChar(char: bidExchangeCode)), \ bidPrice=\(bidPrice), \ bidSize=\(bidSize), \ -askTime=\(TimeUtil.toLocalDateStringWithoutMillis(millis: askTime)), \ +askTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: askTime)) ?? ""), \ askExchange=\(StringUtil.encodeChar(char: askExchangeCode)), \ askPrice=\(askPrice), \ askSize=\(askSize) diff --git a/DXFeedFramework/Events/Market/Series.swift b/DXFeedFramework/Events/Market/Series.swift index 25e09f4d8..cbe6a6fb5 100644 --- a/DXFeedFramework/Events/Market/Series.swift +++ b/DXFeedFramework/Events/Market/Series.swift @@ -109,10 +109,10 @@ extension Series { return """ Series{\(eventSymbol), \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ eventFlags=\(eventFlags.toHexString()), \ index=\(index.toHexString()), \ -time=\(TimeUtil.toLocalDateString(millis: time)), \ +time=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: time)) ?? ""), \ sequence=\(self.getSequence()), \ expiration=\(DayUtil.getYearMonthDayByDayId(Int(expiration))), \ volatility=\(volatility), \ diff --git a/DXFeedFramework/Events/Market/Summary.swift b/DXFeedFramework/Events/Market/Summary.swift index 52602e449..4ef20df31 100644 --- a/DXFeedFramework/Events/Market/Summary.swift +++ b/DXFeedFramework/Events/Market/Summary.swift @@ -119,7 +119,7 @@ extension Summary { return """ Summary{\(eventSymbol), \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ day=\(DayUtil.getYearMonthDayByDayId(dayId)), \ dayOpen=\(dayOpenPrice), \ dayHigh=\(dayHighPrice), \ diff --git a/DXFeedFramework/Events/Market/TheoPrice.swift b/DXFeedFramework/Events/Market/TheoPrice.swift index ab4c1fd2e..47434af7f 100644 --- a/DXFeedFramework/Events/Market/TheoPrice.swift +++ b/DXFeedFramework/Events/Market/TheoPrice.swift @@ -110,9 +110,9 @@ extension TheoPrice { public func toString() -> String { return """ TheoPrice{\(eventSymbol) \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ eventFlags=\(eventFlags.toHexString()), \ -time=\(TimeUtil.toLocalDateString(millis: time)), \ +time=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: time)) ?? ""), \ sequence=\(self.getSequence()), \ price=\(price) \ underlyingPrice=\(underlyingPrice), \ diff --git a/DXFeedFramework/Events/Market/TimeAndSale.swift b/DXFeedFramework/Events/Market/TimeAndSale.swift index 03a23b8ee..13549943a 100644 --- a/DXFeedFramework/Events/Market/TimeAndSale.swift +++ b/DXFeedFramework/Events/Market/TimeAndSale.swift @@ -255,9 +255,9 @@ extension TimeAndSale { public func toString() -> String { return """ TimeAndSale{\(eventSymbol), \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ eventFlags=\(eventFlags.toHexString()), \ -time=\(TimeUtil.toLocalDateString(millis: time)), \ +time=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: time)) ?? ""), \ timeNanoPart=\(timeNanoPart), \ sequence=\(getSequence()), \ exchange=\(StringUtil.encodeChar(char: exchangeCode)), \ diff --git a/DXFeedFramework/Events/Market/Underlying.swift b/DXFeedFramework/Events/Market/Underlying.swift index 0fc7991c2..9e5853bd9 100644 --- a/DXFeedFramework/Events/Market/Underlying.swift +++ b/DXFeedFramework/Events/Market/Underlying.swift @@ -111,9 +111,9 @@ extension Underlying { public func toString() -> String { return """ Underlying{"\(eventSymbol) \ -eventTime=\(TimeUtil.toLocalDateString(millis: eventTime)), \ +eventTime=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: eventTime)) ?? ""), \ eventFlags=\(eventFlags.toHexString()), \ -time=\(TimeUtil.toLocalDateString(millis: time)), \ +time=\((try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: time)) ?? ""), \ sequence=\(self.getSequence()), \ volatility=\(volatility), \ frontVolatility=\(frontVolatility), \ diff --git a/DXFeedFramework/Native/ErrorHandling/ErrorCheck.swift b/DXFeedFramework/Native/ErrorHandling/ErrorCheck.swift index 2ba6f5acd..0bb6873ea 100644 --- a/DXFeedFramework/Native/ErrorHandling/ErrorCheck.swift +++ b/DXFeedFramework/Native/ErrorHandling/ErrorCheck.swift @@ -11,14 +11,35 @@ import Foundation /// Utility class for check native calls. /// The location of the imported functions is in the header files "dxfg_catch_exception.h". class ErrorCheck { + + enum Result: Int32 { + case success = 0 + } + static func test() throws { let exception = GraalException.undefined throw exception } + + @discardableResult + static func nativeCall(_ thread: OpaquePointer!, _ code: Int64) throws -> Int64 { + if code < Result.success.rawValue { + if let exception = fetchException(thread) { + throw exception + } + return code + } else { + return code + } + } + @discardableResult static func nativeCall(_ thread: OpaquePointer!, _ code: Int32) throws -> Int32 { - if code < 0 { - throw fetchException(thread) + if code < Result.success.rawValue { + if let exception = fetchException(thread) { + throw exception + } + return code } else { return code } @@ -28,7 +49,13 @@ class ErrorCheck { if let result = result { return result } else { - throw fetchException(thread) + if let exception = fetchException(thread) { + throw exception + } else { + throw GraalException.fail(message: "Something went wrong. Graal exception is empty", + className: "", + stack: "") + } } } @@ -39,7 +66,7 @@ class ErrorCheck { } } - private static func fetchException(_ thread: OpaquePointer!) -> GraalException { + private static func fetchException(_ thread: OpaquePointer!) -> GraalException? { let exception = dxfg_get_and_clear_thread_exception_t(thread) if let pointee = exception?.pointee { let message = String(pointee: pointee.message, default: "Graall Exception") @@ -51,10 +78,8 @@ class ErrorCheck { dxfg_Exception_release(thread, exception) return gException } else { - return GraalException.fail(message: "Something went wrong. Graal exception is empty", - className: "", stack: "") + return nil } - } } diff --git a/DXFeedFramework/Native/Utils/NativeTimeFormat.swift b/DXFeedFramework/Native/Utils/NativeTimeFormat.swift index 2b6b3548f..96bad4eed 100644 --- a/DXFeedFramework/Native/Utils/NativeTimeFormat.swift +++ b/DXFeedFramework/Native/Utils/NativeTimeFormat.swift @@ -55,4 +55,5 @@ class NativeTimeFormat: NativeBox { let timeFormat = try ErrorCheck.nativeCall(thread, dxfg_TimeFormat_asFullIso(thread, timeFormat.native)) self.init(native: timeFormat) } + } diff --git a/DXFeedFramework/Native/Utils/NativeTimePeriod.swift b/DXFeedFramework/Native/Utils/NativeTimePeriod.swift index d98db6fed..fd80623c2 100644 --- a/DXFeedFramework/Native/Utils/NativeTimePeriod.swift +++ b/DXFeedFramework/Native/Utils/NativeTimePeriod.swift @@ -43,4 +43,22 @@ class NativeTimePeriod: NativeBox { let timePeriod = try ErrorCheck.nativeCall(thread, dxfg_TimePeriod_valueOf2(thread, value.toCStringRef())) self.init(native: timePeriod) } + + func getTime() throws -> Long { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimePeriod_getTime(thread, native)) + return result + } + + func getSeconds() throws -> Int32 { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimePeriod_getSeconds(thread, native)) + return result + } + + func getNanos() throws -> Long { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimePeriod_getNanos(thread, native)) + return result + } } diff --git a/DXFeedFramework/Native/Utils/NativeTimeUtil.swift b/DXFeedFramework/Native/Utils/NativeTimeUtil.swift index beef86c5b..e9f8e1fc1 100644 --- a/DXFeedFramework/Native/Utils/NativeTimeUtil.swift +++ b/DXFeedFramework/Native/Utils/NativeTimeUtil.swift @@ -9,5 +9,17 @@ import Foundation @_implementationOnly import graal_api class NativeTimeUtil { - + + static func parse(timeFormat: NativeTimeFormat, value: String) throws -> Long { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeFormat_parse(thread, timeFormat.native, value.toCStringRef())) + return result + } + + static func format(timeFormat: NativeTimeFormat, value: Long) throws -> String { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeFormat_format(thread, timeFormat.native, value)) + return String(pointee: result) + } + } diff --git a/DXFeedFramework/Native/Utils/NativeTimeZone.swift b/DXFeedFramework/Native/Utils/NativeTimeZone.swift index 052b2e6db..90db26864 100644 --- a/DXFeedFramework/Native/Utils/NativeTimeZone.swift +++ b/DXFeedFramework/Native/Utils/NativeTimeZone.swift @@ -28,4 +28,93 @@ class NativeTimeZone: NativeBox { let native = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_getTimeZone(thread, timeZoneID.toCStringRef())) self.init(native: native) } + + func id() throws -> String? { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_getID(thread, native)) + return String(nullable: result) + } + + func diplayName() throws -> String? { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_getDisplayName(thread, native)) + return String(nullable: result) + } + + func diplayName(dayLight: Int32, style: Int32) throws -> String? { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_getDisplayName2(thread, native, dayLight, style)) + return String(nullable: result) + } + + func getDSTSavings() throws -> Int32 { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_getDSTSavings(thread, native)) + return result + } + + func useDaylightTime() throws -> Int32 { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_useDaylightTime(thread, native)) + return result + } + + func observesDaylightTime() throws -> Int32 { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_observesDaylightTime(thread, native)) + return result + } + + func getOffset(date: Int64) throws -> Int32 { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_getOffset(thread, native, date)) + return result + } + + func getOffset2(era: Int32, + year: Int32, + month: Int32, + day: Int32, + dayOfWeek: Int32, + milliseconds: Int32) throws -> Int32 { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_getOffset2(thread, + native, + era, + year, + month, + day, + dayOfWeek, + milliseconds)) + return result + } + + func getRawOffset() throws -> Int32 { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_getRawOffset(thread, native)) + return result + } + + func hasSameRules(other: NativeTimeZone) throws -> Int32 { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_hasSameRules(thread, native, other.native)) + return result + } + + func inDaylightTime(date: Int64) throws -> Int32 { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_inDaylightTime(thread, native, date)) + return result + } + func setID(id: String) throws -> Bool { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_setID(thread, native, id.toCStringRef())) + return result == ErrorCheck.Result.success.rawValue + } + + func setRawOffset(offsetMillis: Int32) throws -> Bool { + let thread = currentThread() + let result = try ErrorCheck.nativeCall(thread, dxfg_TimeZone_setRawOffset(thread, native, offsetMillis)) + return result == ErrorCheck.Result.success.rawValue + } } diff --git a/DXFeedFramework/Utils/DateTime/DXTimeFormat.swift b/DXFeedFramework/Utils/DateTime/DXTimeFormat.swift index de06dda8f..8d573415d 100644 --- a/DXFeedFramework/Utils/DateTime/DXTimeFormat.swift +++ b/DXFeedFramework/Utils/DateTime/DXTimeFormat.swift @@ -7,7 +7,11 @@ import Foundation +/// Utility class for parsing and formatting dates and times in ISO-compatible format. +/// public class DXTimeFormat { + + /// An instance of TimeFormat that corresponds to default timezone public static let defaultTimeFormat: DXTimeFormat? = { if let timeFormat = NativeTimeFormat.defaultTimeFormat() { return DXTimeFormat(timeFormat: timeFormat) @@ -16,6 +20,7 @@ public class DXTimeFormat { } }() + /// An instance of TimeFormat that corresponds to GMT timezone public static let gmtTimeFormat: DXTimeFormat? = { if let timeFormat = NativeTimeFormat.gmtTimeFormat() { return DXTimeFormat(timeFormat: timeFormat) @@ -24,29 +29,161 @@ public class DXTimeFormat { } }() - private var timeFormat: NativeTimeFormat + internal var timeFormat: NativeTimeFormat private init(timeFormat: NativeTimeFormat) { self.timeFormat = timeFormat } + /// An instance of TimeFormat With Millis that corresponds to default timezone + public lazy var withMillis: DXTimeFormat? = { + return try? DXTimeFormat(withMillis: self) + }() + + + /// Returns TimeFormat instance for a specified timezone. + /// - Throws: GraalException. Rethrows exception from Java. public convenience init(timeZone: DXTimeZone) throws { let timeFormat = try NativeTimeFormat(timeZone: timeZone.timeZone) self.init(timeFormat: timeFormat) } + /// Returns TimeFormat instance that also includes timezone into string + /// - Throws: GraalException. Rethrows exception from Java. public convenience init(withTimeZone timeFormat: DXTimeFormat) throws { let timeFormat = try NativeTimeFormat(withTimeZone: timeFormat.timeFormat) self.init(timeFormat: timeFormat) } + /// Returns TimeFormat instance that also includes milliseconds into string + /// - Throws: GraalException. Rethrows exception from Java. public convenience init(withMillis timeFormat: DXTimeFormat) throws { let timeFormat = try NativeTimeFormat(withMillis: timeFormat.timeFormat) self.init(timeFormat: timeFormat) } - + + /// Returns TimeFormat instance that produces full ISO8610 string of "yyyy-MM-dd'T'HH:mm:ss.SSSX". + /// - Throws: GraalException. Rethrows exception from Java. public convenience init(fullIso timeFormat: DXTimeFormat) throws { let timeFormat = try NativeTimeFormat(fullIso: timeFormat.timeFormat) self.init(timeFormat: timeFormat) } + +} + +public extension DXTimeFormat { + /// Converts the specified string representation of a date and time + /// + /// If no time zone is specified in the parsed string, the string is assumed to denote a local time, + /// and converted to current Date. + /// + /// It accepts the following formats. + /// + /// **0** + /// + /// is parsed as zero time in UTC. + /// + /// **long-value-in-milliseconds** + /// + /// The value in milliseconds since Unix epoch since Unix epoch. + /// It should be positive and have at least 9 digits + /// (otherwise it could not be distinguished from date in format 'yyyymmdd'). + /// Each date since 1970-01-03 can be represented in this form. + /// + /// + /// **date**[time][timezone] + /// If time is missing it is supposed to be '00:00:00'. + /// + /// + /// **date** is one of: + /// + /// yyyy-MM-dd + /// + /// yyyyMMdd + /// + /// + /// **time** is one of: + /// + /// HH:mm:ss[.sss] + /// + /// HHmmss[.sss] + /// + /// + /// **timezone** is one of: + /// + /// [+-]HH:mm + /// + /// [+-]HHmm + /// + /// Z for UTC. + /// + /// - Parameters: + /// - string: String value to parse. + /// - Returns: Timeinterval since 1 Jan 1970, in milliseconds + func parse(_ value: String) throws -> Long? { + return try NativeTimeUtil.parse(timeFormat: timeFormat, value: value) + } + + /// Converts the specified string representation of a date and time + /// + /// If no time zone is specified in the parsed string, the string is assumed to denote a local time, + /// and converted to current Date. + /// + /// It accepts the following formats. + /// + /// **0** + /// + /// is parsed as zero time in UTC. + /// + /// **long-value-in-milliseconds** + /// + /// The value in milliseconds since Unix epoch since Unix epoch. + /// It should be positive and have at least 9 digits + /// (otherwise it could not be distinguished from date in format 'yyyymmdd'). + /// Each date since 1970-01-03 can be represented in this form. + /// + /// + /// **date**[time][timezone] + /// If time is missing it is supposed to be '00:00:00'. + /// + /// + /// **date** is one of: + /// + /// yyyy-MM-dd + /// + /// yyyyMMdd + /// + /// + /// **time** is one of: + /// + /// HH:mm:ss[.sss] + /// + /// HHmmss[.sss] + /// + /// + /// **timezone** is one of: + /// + /// [+-]HH:mm + /// + /// [+-]HHmm + /// + /// Z for UTC. + /// + /// - Parameters: + /// - string: String value to parse. + /// - Returns: Date parsed from value. + func parse(_ value: String) throws -> Date? { + let result = try NativeTimeUtil.parse(timeFormat: timeFormat, value: value) + return Date(millisecondsSince1970: result) + } + + /// Converts object into string according to the format like yyyyMMdd-HHmmss + /// + /// - Parameters: + /// - value: time date and time to format. + /// - Returns: string representation of data and time. + /// - Throws: GraalException. Rethrows exception from Java. + func format(value: Long) throws -> String? { + return try NativeTimeUtil.format(timeFormat: timeFormat, value: value) + } } diff --git a/DXFeedFramework/Utils/DateTime/DXTimePeriod.swift b/DXFeedFramework/Utils/DateTime/DXTimePeriod.swift index b4f6aad9d..04e134d9a 100644 --- a/DXFeedFramework/Utils/DateTime/DXTimePeriod.swift +++ b/DXFeedFramework/Utils/DateTime/DXTimePeriod.swift @@ -7,7 +7,10 @@ import Foundation +/// Value class for period of time with support for ISO8601 duration format. public class DXTimePeriod { + + /// Time-period of zero. public static let zero: DXTimePeriod? = { if let timePeriod = NativeTimePeriod.zero() { return DXTimePeriod(timePeriod: timePeriod) @@ -16,6 +19,7 @@ public class DXTimePeriod { } }() + /// Time-period of "infinity" (time of Int64.max) public static let unlimited: DXTimePeriod? = { if let timePeriod = NativeTimePeriod.unlimited() { return DXTimePeriod(timePeriod: timePeriod) @@ -30,13 +34,39 @@ public class DXTimePeriod { self.timePeriod = timePeriod } + /// Returns ``TimePeriod`` with value milliseconds + /// - Throws: GraalException. Rethrows exception from Java. convenience init(value: Int64) throws { let timePeriod = try NativeTimePeriod(value: value) self.init(timePeriod: timePeriod) } - + + /// Returns TimePeriod represented with a given string. + /// + /// Allowable format is ISO8601 duration, but there are some simplifications and modifications available: + /// Letters are case insensitive. + /// Letters "P" and "T" can be omitted. + /// Letter "S" can be also omitted. In this case last number will be supposed to be seconds. + /// Number of seconds can be fractional. So it is possible to define duration accurate within milliseconds. + /// Every part can be omitted. It is supposed that it's value is zero then. + /// String "inf" recognized as unlimited period. + /// - Throws: GraalException. Rethrows exception from Java. convenience init(value: String) throws { let timePeriod = try NativeTimePeriod(value: value) self.init(timePeriod: timePeriod) } + /// Returns value in milliseconds. + public func getTime() throws -> Long { + return try timePeriod.getTime() + } + + /// Returns value in seconds + public func getSeconds() throws -> Int32 { + return try timePeriod.getSeconds() + } + + /// Returns value in nanoseconds. + public func getNanos() throws -> Long { + return try timePeriod.getNanos() + } } diff --git a/DXFeedFramework/Utils/DateTime/DXTimeZone.swift b/DXFeedFramework/Utils/DateTime/DXTimeZone.swift index c1437b25f..a38c9d8ac 100644 --- a/DXFeedFramework/Utils/DateTime/DXTimeZone.swift +++ b/DXFeedFramework/Utils/DateTime/DXTimeZone.swift @@ -6,7 +6,16 @@ // import Foundation - +/// It is just wrapper aroung Java TimeZone +/// +/// TimeZone represents a time zone offset, and also figures out daylight savings. +/// +/// Typically, you get a TimeZone using getDefault which creates a TimeZone based on the time zone where the program is running. For example, for a program running in Japan, getDefault creates a TimeZone object based on Japanese Standard Time. +/// +/// You can also get a TimeZone using getTimeZone along with a time zone ID. For instance, the time zone ID for the U.S. Pacific Time zone is "America/Los_Angeles". So, you can get a U.S. Pacific Time TimeZone object with. +/// All methods throw exception: GraalException. Rethrows exception from Java. +/// For more details +/// see [Javadoc](https://docs.oracle.com/javase/8/docs/api/java/util/TimeZone.html) public class DXTimeZone { public static let defaultTimeZone: DXTimeZone? = { if let timeZone = NativeTimeZone.defaultTimeZone() { @@ -16,7 +25,7 @@ public class DXTimeZone { } }() - internal var timeZone: NativeTimeZone + internal let timeZone: NativeTimeZone private init(timeZone: NativeTimeZone) { self.timeZone = timeZone @@ -25,4 +34,61 @@ public class DXTimeZone { public convenience init(timeZoneID: String) throws { self.init(timeZone: try NativeTimeZone(timeZoneID: timeZoneID)) } + + public func id() throws -> String? { + return try self.timeZone.id() + } + + public func diplayName() throws -> String? { + return try self.timeZone.diplayName() + } + + public func diplayName(dayLight: Int32, style: Int32) throws -> String? { + return try self.timeZone.diplayName(dayLight: dayLight, style: style) + } + + public func getDSTSavings() throws -> Int32 { + return try self.timeZone.getDSTSavings() + } + + public func useDaylightTime() throws -> Int32 { + return try self.timeZone.useDaylightTime() + } + + public func observesDaylightTime() throws -> Int32 { + return try self.timeZone.observesDaylightTime() + } + + public func getOffset(date: Int64) throws -> Int32 { + return try self.timeZone.getOffset(date: date) + } + + public func getOffset2(era: Int32, year: Int32, month: Int32, day: Int32, dayOfWeek: Int32, milliseconds: Int32) throws -> Int32 { + return try self.timeZone.getOffset2(era: era, + year: year, + month: month, + day: day, + dayOfWeek: dayOfWeek, + milliseconds: milliseconds) + } + + public func getRawOffset() throws -> Int32 { + return try self.timeZone.getRawOffset() + } + + public func hasSameRules(other: DXTimeZone) throws -> Int32 { + return try self.timeZone.hasSameRules(other: other.timeZone) + } + + public func inDaylightTime(date: Int64) throws -> Int32 { + return try self.timeZone.inDaylightTime(date: date) + } + + public func setID(id: String) throws -> Bool { + return try self.timeZone.setID(id: id) + } + + public func setRawOffset(offsetMillis: Int32) throws -> Bool { + return try self.timeZone.setRawOffset(offsetMillis: offsetMillis) + } } diff --git a/DXFeedFramework/Utils/TimeFormat.swift b/DXFeedFramework/Utils/TimeFormat.swift deleted file mode 100644 index 5bb8480e0..000000000 --- a/DXFeedFramework/Utils/TimeFormat.swift +++ /dev/null @@ -1,63 +0,0 @@ -// -// TimeFormat.swift -// DXFeedFramework -// -// Created by Aleksey Kosylo on 28.09.23. -// - -import Foundation - -class TimeFormat { - /// Default format string. - /// Example: - /// 20090615-134530. - static let defaultFormat = "yyyyMMdd-HHmmss" - - /// Format string for only date representation. - /// Example: - /// 20090615. - static let onlyDateFormat = "yyyyMMdd" - - /// Format string with milliseconds. - static let withMillisFormat = ".SSSS" - - /// Format string with TimeZone. - static let withTimeZoneFormat = "zzz" - - /// Full ISO format string. - /// Example: - /// 2009-06-15T13:45:30.0000000Z. - static let fullIsoFormat = "o" - - /// Sortable date/time format string. - /// Example: - /// 2009-06-15T13:45:30. - static let sortableFormat = "yyyy-MM-dd'T'HH:mm:ss" - - /// Universal format string. - /// Example: - /// 2009-06-15 13:45:30Z. - static let universalFormat = "yyyy-MM-dd HH:mm:ssZ" - - static let defaultDateTime = "yyyy-MM-dd HH:mm:ss" - static let defaultDate = "yyyy-MM-dd" - - static let availableFormats = [ - defaultFormat, - "\(defaultFormat)\(withMillisFormat)", - "\(defaultFormat)\(withTimeZoneFormat)", - "\(defaultFormat)Z", - "\(defaultFormat)\(withMillisFormat)\(withTimeZoneFormat)", - "\(defaultFormat)\(withMillisFormat)Z", - onlyDateFormat, - "\(onlyDateFormat)\(withTimeZoneFormat)", - "\(onlyDateFormat)Z", - fullIsoFormat, - sortableFormat, - universalFormat, - "\(defaultDate)Z", - defaultDate, - defaultDateTime, - "\(defaultDateTime)\(withMillisFormat)\(withTimeZoneFormat)" - ] -} diff --git a/DXFeedFramework/Utils/TimeUtil.swift b/DXFeedFramework/Utils/TimeUtil.swift index 188434a81..8d3fcb47d 100644 --- a/DXFeedFramework/Utils/TimeUtil.swift +++ b/DXFeedFramework/Utils/TimeUtil.swift @@ -28,22 +28,6 @@ public class TimeUtil { return Int(MathUtil.floorMod(timeMillis, second)) } - public static func toLocalDateString(millis: Int64) -> String { - if millis == 0 { - return "0" - } - let timeInterval = Double(millis) / 1000 - return (dateFormatterWithMillis.string(from: Date(timeIntervalSince1970: timeInterval))) - } - - public static func toLocalDateStringWithoutMillis(millis: Int64) -> String { - if millis == 0 { - return "0" - } - let timeInterval = Double(millis) / 1000 - return (dateFormatter.string(from: Date(timeIntervalSince1970: timeInterval))) - } - public static func getSecondsFromTime(_ timeMillis: Long) -> Int { if timeMillis >= 0 { return min(Int(timeMillis / second), Int.max) @@ -51,79 +35,4 @@ public class TimeUtil { return max(Int((timeMillis + 1) / second) - 1, Int.min) } } - - /// Converts the specified string representation of a date and time - /// - /// If no time zone is specified in the parsed string, the string is assumed to denote a local time, - /// and converted to current Date. - /// - /// It accepts the following formats. - /// - /// **0** - /// - /// is parsed as zero time in UTC. - /// - /// **long-value-in-milliseconds** - /// - /// The value in milliseconds since Unix epoch since Unix epoch. - /// It should be positive and have at least 9 digits - /// (otherwise it could not be distinguished from date in format 'yyyymmdd'). - /// Each date since 1970-01-03 can be represented in this form. - /// - /// - /// **date**[time][timezone] - /// If time is missing it is supposed to be '00:00:00'. - /// - /// - /// **date** is one of: - /// - /// yyyy-MM-dd - /// - /// yyyyMMdd - /// - /// - /// **time** is one of: - /// - /// HH:mm:ss[.sss] - /// - /// HHmmss[.sss] - /// - /// - /// **timezone** is one of: - /// - /// [+-]HH:mm - /// - /// [+-]HHmm - /// - /// Z for UTC. - /// - /// - Parameters: - /// - string: String value to parse. - /// - Returns: Date parsed from value. - public static func parse(_ string: String) -> Date? { - let trimmed = string.trimmingCharacters(in: .whitespacesAndNewlines) - if trimmed == "0" { - return Date(timeIntervalSince1970: 0) - } - let formatter = DateFormatter() - for format in TimeFormat.availableFormats { - - if format == TimeFormat.sortableFormat { - print("format ") - } - formatter.dateFormat = format - if let date = formatter.date(from: trimmed) { - return date - } - } - if let date = ISO8601DateFormatter().date(from: trimmed) { - return date - } - - if let msValue = Long(string) { - return Date(millisecondsSince1970: msValue) - } - return nil - } - } diff --git a/DXFeedFrameworkTests/DateTimeParserTest.swift b/DXFeedFrameworkTests/DateTimeParserTest.swift index 24986c8a7..81ff64ce5 100644 --- a/DXFeedFrameworkTests/DateTimeParserTest.swift +++ b/DXFeedFrameworkTests/DateTimeParserTest.swift @@ -9,7 +9,6 @@ import XCTest @testable import DXFeedFramework final class DateTimeParserTest: XCTestCase { - override func setUpWithError() throws { // Put setup code here. This method is called before the invocation of each test method in the class. } @@ -19,7 +18,8 @@ final class DateTimeParserTest: XCTestCase { } func testZero() { - XCTAssert(TimeUtil.parse(" 0 ") == Date(millisecondsSince1970: 0)) + let date: Date? = try? DXTimeFormat.defaultTimeFormat?.parse(" 0 ") + XCTAssert(date == Date(millisecondsSince1970: 0)) } private func checkDate(_ date: Date?, components: DateComponents) { @@ -32,23 +32,23 @@ final class DateTimeParserTest: XCTestCase { let dateComponents = calendar.dateComponents(in: components.timeZone ?? TimeZone.current, from: date) print(components) print(dateComponents) - XCTAssert(components.year == dateComponents.year) - XCTAssert(components.month == dateComponents.month) - XCTAssert(components.day == dateComponents.day) - XCTAssert(components.hour == dateComponents.hour) - XCTAssert(components.minute == dateComponents.minute) - XCTAssert(components.second == dateComponents.second) + XCTAssert(components.year == dateComponents.year, "\(date) Not equals \(components)") + XCTAssert(components.month == dateComponents.month, "\(date) Not equals \(components)") + XCTAssert(components.day == dateComponents.day, "\(date) Not equals \(components)") + XCTAssert(components.hour == dateComponents.hour, "\(date) Not equals \(components)") + XCTAssert(components.minute == dateComponents.minute, "\(date) Not equals \(components)") + XCTAssert(components.second == dateComponents.second, "\(date) Not equals \(components)") } func testDate1() { - checkDate(TimeUtil.parse("20070101-123456"), + checkDate(try? DXTimeFormat.defaultTimeFormat?.parse("20070101-123456"), components: DateComponents(year: 2007, month: 01, day: 01, hour: 12, minute: 34, second: 56)) - checkDate(TimeUtil.parse("20070101-123456.123"), + checkDate(try? DXTimeFormat.defaultTimeFormat?.parse("20070101-123456.123"), components: DateComponents(year: 2007, month: 01, day: 01, hour: 12, minute: 34, second: 56)) - checkDate(TimeUtil.parse("2005-12-31 21:00:00"), + checkDate(try? DXTimeFormat.defaultTimeFormat?.parse("2005-12-31 21:00:00"), components: DateComponents(year: 2005, month: 12, day: 31, hour: 21, minute: 0, second: 0)) - checkDate(TimeUtil.parse("2005-12-31 21:00:00.123+03:00"), + checkDate(try? DXTimeFormat.defaultTimeFormat?.parse("2005-12-31 21:00:00.123+03:00"), components: DateComponents(timeZone: TimeZone(secondsFromGMT: 3 * 60 * 60), year: 2005, @@ -57,7 +57,7 @@ final class DateTimeParserTest: XCTestCase { hour: 21, minute: 0, second: 0)) - checkDate(TimeUtil.parse("2005-12-31 23:10:00.123+0400"), + checkDate(try? DXTimeFormat.defaultTimeFormat?.parse("2005-12-31 23:10:00.123+0400"), components: DateComponents(timeZone: TimeZone(secondsFromGMT: 4 * 60 * 60), year: 2005, @@ -66,7 +66,7 @@ final class DateTimeParserTest: XCTestCase { hour: 23, minute: 10, second: 0)) - checkDate(TimeUtil.parse("2007-11-02Z"), + checkDate(try? DXTimeFormat.defaultTimeFormat?.parse("2007-11-02Z"), components: DateComponents(timeZone: TimeZone(identifier: "UTC"), year: 2007, month: 11, @@ -78,15 +78,7 @@ final class DateTimeParserTest: XCTestCase { } func testDate2() { - checkDate(TimeUtil.parse("1"), - components: DateComponents(timeZone: TimeZone(identifier: "UTC"), - year: 1970, - month: 1, - day: 1, - hour: 0, - minute: 0, - second: 0)) - checkDate(TimeUtil.parse("2005-11-30 21:00:00Z"), + checkDate(try? DXTimeFormat.defaultTimeFormat?.parse("2005-11-30 21:00:00Z"), components: DateComponents(timeZone: TimeZone(identifier: "UTC"), year: 2005, @@ -95,7 +87,7 @@ final class DateTimeParserTest: XCTestCase { hour: 21, minute: 0, second: 0)) - checkDate(TimeUtil.parse("2005-11-30T21:00:00Z"), + checkDate(try? DXTimeFormat.defaultTimeFormat?.parse("2005-11-30T21:00:00Z"), components: DateComponents(timeZone: TimeZone(identifier: "UTC"), year: 2005, @@ -104,7 +96,7 @@ final class DateTimeParserTest: XCTestCase { hour: 21, minute: 0, second: 0)) - checkDate(TimeUtil.parse("2005-11-30T21:00:00"), + checkDate(try? DXTimeFormat.defaultTimeFormat?.parse("2005-11-30T21:00:00"), components: DateComponents(year: 2005, month: 11, day: 30, @@ -112,5 +104,10 @@ final class DateTimeParserTest: XCTestCase { minute: 0, second: 0)) } - + + func testWrongDate() { + let date: Date? = try? DXTimeFormat.defaultTimeFormat?.parse("1") + XCTAssert(date == nil) + } + } diff --git a/Samples/IpfTableApp/ViewController.swift b/Samples/IpfTableApp/ViewController.swift index 3df338573..da650e148 100644 --- a/Samples/IpfTableApp/ViewController.swift +++ b/Samples/IpfTableApp/ViewController.swift @@ -99,7 +99,7 @@ extension ViewController: DXInstrumentProfileUpdateListener { self.ipfTableView.reloadData() self.lastUpdateLabel.text = """ -\(self.ipfList.count) profiles: \(TimeUtil.toLocalDateString(millis: self.collector?.getLastUpdateTime() ?? 0)) +\(self.ipfList.count) profiles: \(try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: self.collector?.getLastUpdateTime() ?? 0)) """ } diff --git a/Samples/Tools/LiveIpfSample.swift b/Samples/Tools/LiveIpfSample.swift index 58eb15ec4..3f38cd9fb 100644 --- a/Samples/Tools/LiveIpfSample.swift +++ b/Samples/Tools/LiveIpfSample.swift @@ -96,7 +96,7 @@ extension LiveIpfSample: DXInstrumentProfileUpdateListener { Instrument Profiles: Total number of profiles (1): \(self.ipfList.count) -Last modified: \(TimeUtil.toLocalDateString(millis: collector?.getLastUpdateTime() ?? 0)) +Last modified: \(try? DXTimeFormat.defaultTimeFormat?.withMillis?.format(value: collector?.getLastUpdateTime() ?? 0)) """ ) } diff --git a/Samples/Tools/SubscriptionUtils.swift b/Samples/Tools/SubscriptionUtils.swift index f6e78ba06..776d352d5 100644 --- a/Samples/Tools/SubscriptionUtils.swift +++ b/Samples/Tools/SubscriptionUtils.swift @@ -34,7 +34,7 @@ Create subscription to \(address) for \(types):\(symbols) with properties:\(prop let subscription = try? endpoint?.getFeed()?.createSubscription(str) try? subscription?.add(listener: listener) if time != nil { - guard let date = TimeUtil.parse(time!) else { + guard let date: Date = try? DXTimeFormat.defaultTimeFormat?.parse(time!) else { fatalError("Couldn't parse string \(time ?? "") to Date object") } let timeSubscriptionSymbols = symbols.map { symbol in