diff --git a/libraries/MTConnect.NET-Common/UnixTime.cs b/libraries/MTConnect.NET-Common/UnixTime.cs
index 4ff7de81..b2434173 100644
--- a/libraries/MTConnect.NET-Common/UnixTime.cs
+++ b/libraries/MTConnect.NET-Common/UnixTime.cs
@@ -35,6 +35,39 @@ public static long ToUnixTime(this DateTime d)
}
+ ///
+ /// Convert a DateTime to Unix ticks (1/10,000 of a millisecond) ensuring the value is in UTC.
+ /// If the DateTime.Kind is Local, it will be converted to UTC. If Unspecified, the value will be
+ /// treated as UTC by default (for backwards compatibility) or as the specified kind, then converted to UTC.
+ ///
+ /// The DateTime to convert.
+ /// The kind to assume when DateTime.Kind is Unspecified. Defaults to Utc.
+ /// Unix ticks since epoch in UTC.
+ public static long ToUnixUtcTime(this DateTime d, DateTimeKind unspecifiedAssume = DateTimeKind.Utc)
+ {
+ var x = d;
+ if (x.Kind == DateTimeKind.Local)
+ {
+ x = x.ToUniversalTime();
+ }
+ else if (x.Kind == DateTimeKind.Unspecified)
+ {
+ // Specify the assumed kind, then convert to UTC if necessary
+ x = DateTime.SpecifyKind(x, unspecifiedAssume);
+ if (x.Kind == DateTimeKind.Local) x = x.ToUniversalTime();
+ }
+
+ var duration = x - EpochTime;
+ return duration.Ticks;
+ }
+
+ ///
+ /// Alias to to match requested API name.
+ ///
+ public static long ToUnixUTCTime(this DateTime d, DateTimeKind unspecifiedAssume = DateTimeKind.Utc)
+ => ToUnixUtcTime(d, unspecifiedAssume);
+
+
public static DateTime ToDateTime(this long unixTicks)
{
return FromUnixTime(unixTicks);
diff --git a/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapter.cs b/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapter.cs
index da4e54a4..08c5ea70 100644
--- a/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapter.cs
+++ b/libraries/MTConnect.NET-SHDR/Adapters/ShdrAdapter.cs
@@ -698,7 +698,7 @@ public void AddDataItem(string dataItemKey, object value)
public void AddDataItem(string dataItemKey, object value, DateTime timestamp)
{
- AddDataItem(dataItemKey, value, timestamp.ToUnixTime());
+ AddDataItem(dataItemKey, value, timestamp.ToUnixUtcTime());
}
public void AddDataItem(string dataItemKey, object value, long timestamp)
@@ -735,7 +735,7 @@ public bool SendDataItem(string dataItemKey, object value)
public bool SendDataItem(string dataItemKey, object value, DateTime timestamp)
{
- return SendDataItem(dataItemKey, value, timestamp.ToUnixTime());
+ return SendDataItem(dataItemKey, value, timestamp.ToUnixUtcTime());
}
public bool SendDataItem(string dataItemKey, object value, long timestamp)
@@ -784,7 +784,7 @@ public void AddMessage(string messageId, string value)
public void AddMessage(string messageId, string value, DateTime timestamp)
{
- AddMessage(messageId, value, timestamp.ToUnixTime());
+ AddMessage(messageId, value, timestamp.ToUnixUtcTime());
}
public void AddMessage(string messageId, string value, long timestamp)
@@ -799,7 +799,7 @@ public void AddMessage(string messageId, string value, string nativeCode)
public void AddMessage(string messageId, string value, string nativeCode, DateTime timestamp)
{
- AddMessage(messageId, value, nativeCode, timestamp.ToUnixTime());
+ AddMessage(messageId, value, nativeCode, timestamp.ToUnixUtcTime());
}
public void AddMessage(string messageId, string value, string nativeCode, long timestamp)
@@ -831,7 +831,7 @@ public bool SendMessage(string dataItemId, string value)
public bool SendMessage(string dataItemId, string value, DateTime timestamp)
{
- return SendMessage(dataItemId, value, timestamp.ToUnixTime());
+ return SendMessage(dataItemId, value, timestamp.ToUnixUtcTime());
}
public bool SendMessage(string dataItemId, string value, long timestamp)
@@ -846,7 +846,7 @@ public bool SendMessage(string dataItemId, string value, string nativeCode)
public bool SendMessage(string dataItemId, string value, string nativeCode, DateTime timestamp)
{
- return SendMessage(dataItemId, value, nativeCode, timestamp.ToUnixTime());
+ return SendMessage(dataItemId, value, nativeCode, timestamp.ToUnixUtcTime());
}
public bool SendMessage(string dataItemId, string value, string nativeCode, long timestamp)
diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataItem.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataItem.cs
index 340a4ff9..ee902a91 100644
--- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataItem.cs
+++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrDataItem.cs
@@ -66,7 +66,7 @@ public ShdrDataItem(string dataItemKey, object value, DateTime timestamp)
{
new ObservationValue(ValueKeys.Result, value != null ? value.ToString() : string.Empty)
};
- Timestamp = timestamp.ToUnixTime();
+ Timestamp = timestamp.ToUnixUtcTime();
}
@@ -350,7 +350,7 @@ public static IEnumerable FromString(string input, bool uppercaseV
if (timestamp.HasValue)
{
var y = ShdrLine.GetNextSegment(input);
- return FromKeyValuePairs(y, timestamp.Value.ToUnixTime(), duration.HasValue ? duration.Value : 0, uppercaseValue);
+ return FromKeyValuePairs(y, timestamp.Value.ToUnixUtcTime(), duration.HasValue ? duration.Value : 0, uppercaseValue);
}
else
{
diff --git a/libraries/MTConnect.NET-SHDR/Shdr/ShdrMessage.cs b/libraries/MTConnect.NET-SHDR/Shdr/ShdrMessage.cs
index 603c12d5..33a22b53 100644
--- a/libraries/MTConnect.NET-SHDR/Shdr/ShdrMessage.cs
+++ b/libraries/MTConnect.NET-SHDR/Shdr/ShdrMessage.cs
@@ -82,7 +82,7 @@ public ShdrMessage(string dataItemKey, string value, DateTime timestamp)
{
new ObservationValue(ValueKeys.Result, value != null ? value.ToString() : string.Empty)
};
- Timestamp = timestamp.ToUnixTime();
+ Timestamp = timestamp.ToUnixUtcTime();
}
public ShdrMessage(string dataItemKey, string value, string nativeCode, DateTime timestamp)
@@ -92,7 +92,7 @@ public ShdrMessage(string dataItemKey, string value, string nativeCode, DateTime
values.Add(new ObservationValue(ValueKeys.Result, value != null ? value.ToString() : string.Empty));
if (!string.IsNullOrEmpty(nativeCode)) values.Add(new ObservationValue(ValueKeys.NativeCode, nativeCode));
Values = values;
- Timestamp = timestamp.ToUnixTime();
+ Timestamp = timestamp.ToUnixUtcTime();
}
public ShdrMessage(IObservationInput observation)