public override async Task WriteMessages(string database, IEnumerable<WriteMessage> messages, Consistency? consistency = null, string retentionPolicy = null, DateTime? timestamp = null, TimePrecision? precision = null) { using (var msg = new HttpRequestMessage(HttpMethod.Post, CreateUrl("/write", database, null, null, consistency, retentionPolicy))) { msg.Content = new StringContent(string.Join("\n", messages.Select(x => x.ToString(timestamp, precision))), Encoding.UTF8); using (var response = await _client.SendAsync(msg, HttpCompletionOption.ResponseHeadersRead, CancellationToken.None).ConfigureAwait(false)) { response.ValidateHttpResponse(HttpStatusCode.NoContent, true); } } }
/// <summary> /// Tracks an event. /// </summary> /// <param name="category"> /// Typically the object that was interacted with (e.g. button) /// </param> /// <param name="action"> /// The type of interaction (e.g. click) /// </param> /// <param name="eventId"> /// The id of the thing being interacted with. /// </param> /// <param name="precision"> /// The precision that this event should be tracked at. /// </param> /// <param name="now"> /// The now. /// </param> public static void TrackEvent( string category, string action, long eventId, TimePrecision precision = TimePrecision.OneDay, DateTime now = default(DateTime)) { if (now == default(DateTime)) { now = DateTime.UtcNow; } string time; switch (precision) { case TimePrecision.FifteenMinutes: { time = DateTimeUtil.FifteenMinutes(now); break; } case TimePrecision.OneHour: { time = DateTimeUtil.OneHour(now); break; } case TimePrecision.OneDay: { time = DateTimeUtil.OneDay(now); break; } case TimePrecision.OneMonth: { time = DateTimeUtil.OneMonth(now); break; } default: { throw new Exception(string.Format("unsupported precision encountered\n\t{0}", precision)); } } RedisKey key = EventKey(category, action, time); SharedCache.Instance.GetAnalyticsWriteConnection() .GetDatabase(SharedCache.Instance.Db) .StringSetBit(key, eventId, true); }
public static long ToEpoch(this DateTime time, TimePrecision precision) { TimeSpan t = time - Origin; switch ( precision ) { case TimePrecision.Hours: return (long) t.TotalHours; case TimePrecision.Minutes: return (long) t.TotalMinutes; case TimePrecision.Seconds: return (long) t.TotalSeconds; case TimePrecision.Milliseconds: return (long) t.TotalMilliseconds; case TimePrecision.Microseconds: return (long) t.TotalMilliseconds * 1000; case TimePrecision.Nanoseconds: return (long) t.TotalMilliseconds * 1000 * 1000; } return 0; }
public override async Task<ResultSet> SendQuery(string database, string query, TimePrecision resultPrecision = TimePrecision.Microsecond, CancellationToken cancellationToken = default(CancellationToken)) { using (var message = new HttpRequestMessage(HttpMethod.Post, CreateUrl("/query", database, query))) using (var response = await _client.SendAsync(message, HttpCompletionOption.ResponseContentRead, cancellationToken).ConfigureAwait(false)) { response.ValidateHttpResponse(HttpStatusCode.OK, false); var result = await response.Content .ReadAsAsync<ResultSet>(cancellationToken) .ConfigureAwait(false); return result; } }
public static DateTime FromEpoch (this string time, TimePrecision precision) { long duration = long.Parse (time); DateTime t = Origin; switch (precision) { case TimePrecision.Hours: return t.AddHours (duration); case TimePrecision.Minutes: return t.AddMinutes (duration); case TimePrecision.Seconds: return t.AddSeconds (duration); case TimePrecision.Milliseconds: return t.AddMilliseconds (duration); case TimePrecision.Microseconds: return t.AddTicks (duration * TimeSpan.TicksPerMillisecond * 1000); case TimePrecision.Nanoseconds: return t.AddTicks (duration / 100); //1 tick = 100 nano sec } return t; }
public AdaptiveTimestampGenerator(TimePrecision precision) { Precision = precision; switch (precision) { case TimePrecision.Nanosecond: case TimePrecision.Microsecond: _generator = SystemTimePreciseTimestampSource.IsAvailable ? (Func<DateTime>) GetSystemTimePrecise : GetDateTimeStopwatch; break; default: _generator = GetDateTime; break; } }
public static long ToUnixTime(DateTime date, TimePrecision precision) { switch (precision) { case TimePrecision.Nanosecond: return Convert.ToInt64((date.ToUniversalTime() - Epoch).TotalNanoseconds()); case TimePrecision.Microsecond: return Convert.ToInt64((date.ToUniversalTime() - Epoch).TotalMicroseconds()); case TimePrecision.Millisecond: return Convert.ToInt64((date.ToUniversalTime() - Epoch).TotalMilliseconds); case TimePrecision.Second: return Convert.ToInt64((date.ToUniversalTime() - Epoch).TotalSeconds); case TimePrecision.Minute: return Convert.ToInt64((date.ToUniversalTime() - Epoch).TotalMinutes); case TimePrecision.Hour: return Convert.ToInt64((date.ToUniversalTime() - Epoch).TotalHours); default: throw new ArgumentException("Unsupported precision: " + precision, "precision"); } }
public static DateTime FromEpoch(this string time, TimePrecision precision) { long duration = long.Parse(time); DateTime t = Origin; switch (precision) { case TimePrecision.Hours: return(t.AddHours(duration)); case TimePrecision.Minutes: return(t.AddMinutes(duration)); case TimePrecision.Seconds: return(t.AddSeconds(duration)); case TimePrecision.Milliseconds: return(t.AddMilliseconds(duration)); case TimePrecision.Microseconds: return(t.AddTicks(duration * TimeSpan.TicksPerMillisecond * 1000)); case TimePrecision.Nanoseconds: return(t.AddTicks(duration / 100)); //1 tick = 100 nano sec } return(t); }
/// <summary> /// Convert the Influx Series JSON objects to InfluxSeries /// </summary> /// <param name="precision"></param> /// <param name="series"></param> /// <param name="SafePropertyNames">If true the first letter of each property name will be Capital, making them safer to use in C#</param> /// <returns></returns> private static InfluxSeries GetInfluxSeries(TimePrecision precision, Series series, bool SafePropertyNames = true) { var result = new InfluxSeries() { HasEntries = false }; result.SeriesName = series.Name; result.Tags = series.Tags; var entries = new List <dynamic>(); for (var row = 0; row < series?.Values?.Count; row++) { result.HasEntries = true; dynamic entry = new ExpandoObject(); entries.Add(entry); for (var col = 0; col < series.Columns.Count; col++) { string header; if (SafePropertyNames) { header = char.ToUpper(series.Columns[col][0]) + series.Columns[col].Substring(1); } else { header = series.Columns[col]; } if (String.Equals(header, "Time", StringComparison.OrdinalIgnoreCase)) { ((IDictionary <string, object>)entry).Add(header, EpochHelper.FromEpoch(series.Values[row][col], precision)); } else { ((IDictionary <string, object>)entry).Add(header, series.Values[row][col]); } } } result.Entries = entries; return(result); }
/// <summary> /// Initializes a new instance of the <see cref="Time"/> struct. /// </summary> /// <param name="time">The time.</param> /// <param name="precision">The precision.</param> public Time(Time time, TimePrecision precision) { _precision = precision; switch (precision) { case TimePrecision.WithMilliseconds: _hour = time.Hour; _minute = time.Minute; _second = time.Second; _millisecond = time.Millisecond; break; case TimePrecision.WithSeconds: _hour = time.Hour; _minute = time.Minute; _second = time.Second; _millisecond = 0; break; case TimePrecision.WithMinutes: _hour = time.Hour; _minute = time.Minute; _second = 0; _millisecond = 0; break; case TimePrecision.WithHours: _hour = time.Hour; _minute = 0; _second = 0; _millisecond = 0; break; default: throw new ArgumentOutOfRangeException("precision"); } }
private async Task <bool> PostPointsAsync(string dbName, TimePrecision precision, IEnumerable <IInfluxDatapoint> points) { var influxAddress = new Uri(String.Format("{0}/write?", InfluxUrl)); var builder = new UriBuilder(influxAddress); builder.Query = await new FormUrlEncodedContent(new[] { new KeyValuePair <string, string>("db", dbName), new KeyValuePair <string, string>("precision", precisionLiterals[(int)precision]) }).ReadAsStringAsync(); var line = new StringBuilder(); foreach (var point in points) { line.AppendFormat("{0}\n", point.ConvertToInfluxLineProtocol()); } //remove last \n line.Remove(line.Length - 1, 1); ByteArrayContent requestContent = new ByteArrayContent(Encoding.UTF8.GetBytes(line.ToString())); HttpResponseMessage response = await PostAsync(builder, requestContent); if (response.StatusCode == HttpStatusCode.Unauthorized || response.StatusCode == HttpStatusCode.BadGateway || (response.StatusCode == HttpStatusCode.InternalServerError && response.ReasonPhrase == "INKApi Error")) //502 Connection refused { throw new UnauthorizedAccessException("InfluxDB needs authentication. Check uname, pwd parameters"); } //if(response.StatusCode==HttpStatusCode.NotFound) else if (response.StatusCode == HttpStatusCode.NoContent) { return(true); } else { return(false); } }
/// <summary> /// Posts raw write request to Influx. /// </summary> /// <param name="dbName">Name of the Database</param> /// <param name="precision">Unit of the timestamp, Hour->nanosecond</param> /// <param name="content">Raw request, as per Line Protocol</param> /// <see cref="https://influxdb.com/docs/v0.9/write_protocols/write_syntax.html#http"/> /// <returns>true:success, false:failure</returns> public async Task<bool> PostRawValueAsync (string dbName, TimePrecision precision, string content) { ByteArrayContent requestContent = new ByteArrayContent (Encoding.UTF8.GetBytes (content)); HttpResponseMessage response = await PostAsync (new Dictionary<string, string> () { { "db", dbName }, { "precision", precisionLiterals[(int) precision] } }, requestContent); if (response.StatusCode == HttpStatusCode.NoContent) return true; else return false; }
/// <summary> /// 获取显示时间 /// </summary> /// <param name="ticks"></param> /// <param name="precision">时间精度</param> /// <param name="includeDay">是否显示天数</param> /// <returns></returns> public static string GetTimeText(this long ticks, TimePrecision precision, bool includeDay = true) { return(TimeSpan.FromTicks(ticks).GetTimeText(precision, includeDay)); }
public List<Serie> Query(string query, TimePrecision? precision = null) { string escapedQuery = HttpUtility.UrlEncode(query); string url = this.GetUrl("/db/" + this.database + "/series"); if (precision.HasValue) { url += "&time_precision=" + this.timePrecision[(int) precision.Value]; } url += "&q=" + escapedQuery; object result = this.Request(url, "GET"); if (result != null) { return JsonConvert.DeserializeObject<List<Serie>>(result.ToString()); } return null; }
public SequentialTimestampGenerator(TimePrecision precision) { Precision = precision; }
public InfluxDBClient(string host, int port, bool useHttps, string username, string password, string database, Consistency defaultConsistency, TimePrecision timestampPrecision = TimePrecision.Nanosecond) : this(database, defaultConsistency) { RequestProcessor = new HttpClientRequestProcessor(new RequestProcessorSettings(host, port, useHttps, username, password)); TimestampGenerator = new AdaptiveTimestampGenerator(timestampPrecision); }
/// <summary> /// Queries Influx DB and gets a time series data back. Ideal for fetching measurement values. /// The return list is of InfluxSeries, and each element in there will have properties named after columns in series /// </summary> /// <param name="dbName">Name of the database</param> /// <param name="measurementQuery">Query text, Only results with single series are supported for now</param> /// <param name="precision">epoch precision of the data set</param> /// <returns>List of InfluxSeries</returns> /// <seealso cref="InfluxSeries"/> public async Task<List<IInfluxSeries>> QueryMultiSeriesAsync (string dbName, string measurementQuery, TimePrecision precision = TimePrecision.Nanoseconds) { var response = await GetAsync (new Dictionary<string, string> () { { "db", dbName }, { "q", measurementQuery }, { "epoch", precisionLiterals[(int) precision] } }); if (response.StatusCode == HttpStatusCode.OK) { var results = new List<IInfluxSeries> (); var rawResult = JsonConvert.DeserializeObject<InfluxResponse> (await response.Content.ReadAsStringAsync ()); if (rawResult?.Results?.Count > 1) throw new ArgumentException ("The query is resulting in a format, which is not supported by this method yet"); if (rawResult?.Results[0]?.Series != null) { foreach (var series in rawResult?.Results[0]?.Series) { var result = new InfluxSeries (); result.HasEntries = false; results.Add (result); result.SeriesName = series.Name; result.Tags = series.Tags; var entries = new List<dynamic> (); for (var row = 0; row < series?.Values?.Count; row++) { result.HasEntries = true; dynamic entry = new ExpandoObject (); entries.Add (entry); for (var col = 0; col < series.Columns.Count; col++) { var header = char.ToUpper (series.Columns[col][0]) + series.Columns[col].Substring (1); if (header == "Time") ((IDictionary<string, object>) entry).Add (header, EpochHelper.FromEpoch (series.Values[row][col], precision)); else ((IDictionary<string, object>) entry).Add (header, series.Values[row][col]); } } result.Entries = entries; } } return results; } return null; }
public TimePrecisionAttribute(TimePrecision precision) : base((byte)precision) { Precision = precision; }
public InfluxTimestampGenerator(TimePrecision precision) { Precision = precision; }
public async Task <bool> PostValuesAsync(string dbName, string measurement, long timestamp, TimePrecision precision, string tags, IDictionary <string, double> values) { var influxAddress = new Uri(String.Format("{0}/write?", InfluxUrl)); var builder = new UriBuilder(influxAddress); builder.Query = await new FormUrlEncodedContent(new[] { new KeyValuePair <string, string>("db", dbName), new KeyValuePair <string, string>("precision", precisionLiterals[(int)precision]) }).ReadAsStringAsync(); //var content = new StringBuilder (); //foreach ( var value in values ) // content.AppendFormat ("{0},{1} {2} {3}\n", measurement, tags, value, timestamp); ////remove last \n //content.Remove (content.Length - 1, 1); var valuesTxt = String.Join(",", values.Select(v => String.Format(System.Globalization.CultureInfo.GetCultureInfo("en-US"), "{0}={1}", v.Key, v.Value))); var content = String.Format("{0},{1} {2} {3}", measurement, tags, valuesTxt, timestamp); ByteArrayContent requestContent = new ByteArrayContent(Encoding.UTF8.GetBytes(content.ToString())); HttpResponseMessage response = await PostAsync(builder, requestContent); if (response.StatusCode == HttpStatusCode.Unauthorized || response.StatusCode == HttpStatusCode.BadGateway || (response.StatusCode == HttpStatusCode.InternalServerError && response.ReasonPhrase == "INKApi Error")) //502 Connection refused { throw new UnauthorizedAccessException("InfluxDB needs authentication. Check uname, pwd parameters"); } //if(response.StatusCode==HttpStatusCode.NotFound) else if (response.StatusCode == HttpStatusCode.NoContent) { return(true); } else { return(false); } }
public DateTimeStopwatchTimestampGenerator(TimePrecision precision) { Precision = precision; }
public string ToString(DateTime? timestamp, TimePrecision? precision, double comparisonTolerance = 0.00001) { return Key + " " + Fields.FormatFields(comparisonTolerance) + (timestamp.HasValue ? " " + ToUnixTime(timestamp.Value, (precision ?? TimePrecision.Nanosecond)) : string.Empty); }
/// <summary> /// Queries Influx DB and gets a time series data back. Ideal for fetching measurement values. /// The return list is of InfluxSeries, and each element in there will have properties named after columns in series /// THis uses Chunking support from InfluxDB. It returns results in streamed batches rather than as a single response /// Responses will be chunked by series or by every ChunkSize points, whichever occurs first. /// </summary> /// <param name="dbName">Name of the database</param> /// <param name="measurementQuery">Query text, Only results with single series are supported for now</param> /// <param name="ChunkSize">Maximum Number of points in a chunk</param> /// <param name="precision">epoch precision of the data set</param> /// <returns>List of InfluxSeries</returns> /// <seealso cref="InfluxSeries"/> public async Task <List <IInfluxSeries> > QueryMultiSeriesAsync(string dbName, string measurementQuery, int ChunkSize, TimePrecision precision = TimePrecision.Nanoseconds) { var response = await GetAsync(new Dictionary <string, string>() { { "db", dbName }, { "q", measurementQuery }, { "chunked", "true" }, { "chunk_size", ChunkSize.ToString() }, { "epoch", precisionLiterals[(int)precision] } }); if (response == null) { throw new ServiceUnavailableException(); } if (response.StatusCode == HttpStatusCode.OK) { var results = new List <IInfluxSeries>(); //Hack for https://github.com/influxdata/influxdb/issues/8212 foreach (var str in (await response.Content.ReadAsStringAsync()).Split('\n')) { var rawResult = JsonConvert.DeserializeObject <InfluxResponse>(str); if (rawResult?.Results[0]?.Series != null) { foreach (var series in rawResult?.Results[0]?.Series) { InfluxSeries result = GetInfluxSeries(precision, series); results.Add(result); } } if (!rawResult.Results[0].Partial) { break; } } return(results); } return(null); }
/// <summary> /// Initializes a new instance of the <see cref="TimeRange"/> struct. /// </summary> /// <param name="range">The range.</param> /// <param name="precision">The precision.</param> public TimeRange(TimeRange range, TimePrecision precision) { from = new Time(range.From, precision); to = new Time(range.To, precision); }
/// <summary> /// Posts raw write request to Influx. /// </summary> /// <param name="dbName">Name of the Database</param> /// <param name="precision">Unit of the timestamp, Hour->nanosecond</param> /// <param name="content">Raw request, as per Line Protocol</param> /// <see cref="https://influxdb.com/docs/v0.9/write_protocols/write_syntax.html#http"/> /// <returns>true:success, false:failure</returns> public async Task<bool> PostRawValueAsync(string dbName, TimePrecision precision, string content) { var influxAddress = new Uri (String.Format ("{0}/write?", InfluxUrl)); var builder = new UriBuilder (influxAddress); builder.Query = await new FormUrlEncodedContent (new[] { new KeyValuePair<string, string>("db", dbName) , new KeyValuePair<string, string>("precision", precisionLiterals[(int) precision]) }).ReadAsStringAsync (); ByteArrayContent requestContent = new ByteArrayContent (Encoding.UTF8.GetBytes (content)); HttpResponseMessage response = await PostAsync (builder, requestContent); if ( response.StatusCode == HttpStatusCode.Unauthorized || response.StatusCode == HttpStatusCode.BadGateway || ( response.StatusCode == HttpStatusCode.InternalServerError && response.ReasonPhrase == "INKApi Error" ) ) //502 Connection refused throw new UnauthorizedAccessException ("InfluxDB needs authentication. Check uname, pwd parameters"); //if(response.StatusCode==HttpStatusCode.NotFound) else if ( response.StatusCode == HttpStatusCode.NoContent ) return true; else return false; }
public Task <ResultSet> SendQuery(string query, TimePrecision resultPrecision = TimePrecision.Microsecond, CancellationToken cancellationToken = new CancellationToken()) { return(SendQuery(null, query, resultPrecision, cancellationToken)); }
public async Task<bool> PostValuesAsync(string dbName, string measurement, long timestamp, TimePrecision precision, string tags, IDictionary<string, double> values) { var influxAddress = new Uri (String.Format ("{0}/write?", InfluxUrl)); var builder = new UriBuilder (influxAddress); builder.Query = await new FormUrlEncodedContent (new[] { new KeyValuePair<string, string>("db", dbName) , new KeyValuePair<string, string>("precision", precisionLiterals[(int) precision]) }).ReadAsStringAsync (); //var content = new StringBuilder (); //foreach ( var value in values ) // content.AppendFormat ("{0},{1} {2} {3}\n", measurement, tags, value, timestamp); ////remove last \n //content.Remove (content.Length - 1, 1); var valuesTxt = String.Join (",", values.Select (v => String.Format (System.Globalization.CultureInfo.GetCultureInfo ("en-US"), "{0}={1}", v.Key, v.Value))); var content = String.Format ("{0},{1} {2} {3}", measurement, tags, valuesTxt, timestamp); ByteArrayContent requestContent = new ByteArrayContent (Encoding.UTF8.GetBytes (content.ToString ())); HttpResponseMessage response = await PostAsync (builder, requestContent); if ( response.StatusCode == HttpStatusCode.Unauthorized || response.StatusCode == HttpStatusCode.BadGateway || ( response.StatusCode == HttpStatusCode.InternalServerError && response.ReasonPhrase == "INKApi Error" ) ) //502 Connection refused throw new UnauthorizedAccessException ("InfluxDB needs authentication. Check uname, pwd parameters"); //if(response.StatusCode==HttpStatusCode.NotFound) else if ( response.StatusCode == HttpStatusCode.NoContent ) return true; else return false; }
public override async Task <ResultSet> SendQuery(string database, string query, TimePrecision resultPrecision = TimePrecision.Microsecond, CancellationToken cancellationToken = default(CancellationToken)) { using (var message = new HttpRequestMessage(HttpMethod.Post, CreateUrl("/query", database, query))) using (var response = await _client.SendAsync(message, HttpCompletionOption.ResponseContentRead, cancellationToken).ConfigureAwait(false)) { response.ValidateHttpResponse(HttpStatusCode.OK, false); var result = await response.Content .ReadAsAsync <ResultSet>(cancellationToken) .ConfigureAwait(false); return(result); } }
public abstract Task <ResultSet> SendQuery(string database, string query, TimePrecision resultPrecision = TimePrecision.Microsecond, CancellationToken cancellationToken = new CancellationToken());
/// <summary> /// Queries Influx DB and gets a time series data back. Ideal for fetching measurement values. /// The return list is of InfluxSeries, and each element in there will have properties named after columns in series /// </summary> /// <param name="dbName">Name of the database</param> /// <param name="measurementQuery">Query text, Only results with single series are supported for now</param> /// <param name="precision">epoch precision of the data set</param> /// <returns>List of InfluxSeries</returns> /// <seealso cref="InfluxSeries"/> public async Task <List <IInfluxSeries> > QueryMultiSeriesAsync(string dbName, string measurementQuery, TimePrecision precision = TimePrecision.Nanoseconds) { var response = await GetAsync(new Dictionary <string, string>() { { "db", dbName }, { "q", measurementQuery }, { "epoch", precisionLiterals[(int)precision] } }); if (response == null) { throw new ServiceUnavailableException(); } if (response.StatusCode == HttpStatusCode.OK) { var results = new List <IInfluxSeries>(); var rawResult = JsonConvert.DeserializeObject <InfluxResponse>(await response.Content.ReadAsStringAsync()); if (rawResult?.Results?.Count > 1) { throw new ArgumentException("The query is resulting in a format, which is not supported by this method yet"); } if (rawResult?.Results[0]?.Series != null) { foreach (var series in rawResult?.Results[0]?.Series) { InfluxSeries result = GetInfluxSeries(precision, series); results.Add(result); } } return(results); } return(null); }
public static string HumanReadableDateDiff(DateTime MainDate, DateTime OtherDate, TimePrecision Precision, TimePrecision MaxFallBackPrecision, string Separator, bool WriteSuffix) { string functionReturnValue = null; functionReturnValue = ""; int years = 0; int months = 0; int days = 0; int hours = 0; int minutes = 0; int seconds = 0; int milliseconds = 0; string S_year = "year"; string S_month = "month"; string S_day = "day"; string S_hour = "hour"; string S_minute = "min"; string S_second = "sec"; string S_millisecond = "ms"; string S_years = "years"; string S_months = "months"; string S_days = "days"; string S_hours = "hours"; string S_minutes = "min"; string S_seconds = "sec"; string S_milliseconds = "ms"; string S_now = "now"; string S_ago = "ago"; DateTime BiggerDate = default(DateTime); DateTime SmallestDate = default(DateTime); if (MainDate.CompareTo(OtherDate) >= 0) { BiggerDate = MainDate; SmallestDate = OtherDate; } else { BiggerDate = OtherDate; SmallestDate = MainDate; } while ((BiggerDate.AddYears(-1).CompareTo(SmallestDate) >= 0)) { years += 1; BiggerDate = BiggerDate.AddYears(-1); } while ((BiggerDate.AddMonths(-1).CompareTo(SmallestDate) >= 0)) { months += 1; BiggerDate = BiggerDate.AddMonths(-1); } while ((BiggerDate.AddDays(-1).CompareTo(SmallestDate) >= 0)) { days += 1; BiggerDate = BiggerDate.AddDays(-1); } TimeSpan diff = BiggerDate.Subtract(SmallestDate); hours = diff.Hours; minutes = diff.Minutes; seconds = diff.Seconds; milliseconds = diff.Milliseconds; //precision fallback if ((Precision == TimePrecision.Years) && (MaxFallBackPrecision > TimePrecision.Years) && (years == 0)) { Precision = TimePrecision.Month; } if ((Precision == TimePrecision.Month) && (MaxFallBackPrecision > TimePrecision.Month) && (years == 0) && (months == 0)) { Precision = TimePrecision.Day; } if ((Precision == TimePrecision.Day) && (MaxFallBackPrecision > TimePrecision.Day) && (years == 0) && (months == 0) && (days == 0)) { Precision = TimePrecision.Hour; } if ((Precision == TimePrecision.Hour) && (MaxFallBackPrecision > TimePrecision.Hour) && (years == 0) && (months == 0) && (days == 0) && (hours == 0)) { Precision = TimePrecision.Minute; } if ((Precision == TimePrecision.Minute) && (MaxFallBackPrecision > TimePrecision.Minute) && (years == 0) && (months == 0) && (days == 0) && (hours == 0) && (minutes == 0)) { Precision = TimePrecision.Second; } if ((Precision == TimePrecision.Second) && (MaxFallBackPrecision > TimePrecision.Second) && (years == 0) && (months == 0) && (days == 0) && (hours == 0) && (minutes == 0) && (seconds == 0)) { Precision = TimePrecision.Millisecond; } if (years > 0) { functionReturnValue += string.Format("{0} {1}|", years, (years == 1 ? S_year : S_years)); } if (Precision > TimePrecision.Years && months > 0) { functionReturnValue += string.Format("{0} {1}|", months, (months == 1 ? S_month : S_months)); } if (Precision > TimePrecision.Month && days > 0) { functionReturnValue += string.Format("{0} {1}|", days, (days == 1 ? S_day : S_days)); } if (Precision > TimePrecision.Day && hours > 0) { functionReturnValue += string.Format("{0} {1}|", hours, (hours == 1 ? S_hour : S_hours)); } if (Precision > TimePrecision.Hour && minutes > 0) { functionReturnValue += string.Format("{0} {1}|", minutes, (minutes == 1 ? S_minute : S_minutes)); } if (Precision > TimePrecision.Minute && seconds > 0) { functionReturnValue += string.Format("{0} {1}|", seconds, (seconds == 1 ? S_second : S_seconds)); } if (Precision > TimePrecision.Second && milliseconds > 0) { functionReturnValue += string.Format("{0} {1}|", milliseconds, (milliseconds == 1 ? S_millisecond : S_milliseconds)); } if (functionReturnValue == null || string.IsNullOrEmpty(functionReturnValue)) { if (WriteSuffix) { functionReturnValue = S_now; } } else { functionReturnValue = functionReturnValue.Trim(new char[] { '|' }); functionReturnValue = functionReturnValue.Replace("|", Separator); if (WriteSuffix) { if (MainDate.CompareTo(OtherDate) > 0) { functionReturnValue = functionReturnValue + " " + S_ago; } } } return(functionReturnValue); }
/// <summary> /// Initializes a time control /// </summary> public TimeControl(uint targetFPS, TimePrecision precision) { TargetFPS = targetFPS; Precision = precision; }
public async Task <ResultSet> Query(string query, TimePrecision resultPrecision = TimePrecision.Microsecond, CancellationToken cancellationToken = default(CancellationToken)) { return(await RequestProcessor.SendQuery(query, resultPrecision, cancellationToken).ConfigureAwait(false)); }
public async Task<ResultSet> Query(string query, TimePrecision resultPrecision = TimePrecision.Microsecond, CancellationToken cancellationToken = default(CancellationToken)) { return await RequestProcessor.SendQuery(query, resultPrecision, cancellationToken).ConfigureAwait(false); }
public Task<ResultSet> SendQuery(string query, TimePrecision resultPrecision = TimePrecision.Microsecond, CancellationToken cancellationToken = new CancellationToken()) { return SendQuery(null, query, resultPrecision, cancellationToken); }
public static string TimeSpanToString(TimeSpan Span, TimePrecision Precision, TimePrecision MaxFallBackPrecision, string Separator, bool WriteSuffix) { if (Span >= TimeSpan.MaxValue) { return("+∞"); } else if (Span <= TimeSpan.MinValue) { return("-∞"); } else { DateTime N = DateTime.Now; return(HumanReadableDateDiff(N, N.Add(Span), Precision, MaxFallBackPrecision, Separator, WriteSuffix)); } }
public abstract Task<ResultSet> SendQuery(string database, string query, TimePrecision resultPrecision = TimePrecision.Microsecond, CancellationToken cancellationToken = new CancellationToken());
public abstract Task WriteMessage(string database, WriteMessage message, Consistency? consistency = null, string retentionPolicy = null, DateTime? timestamp = null, TimePrecision? precision = null);
public abstract Task WriteMessages(string database, IEnumerable<WriteMessage> messages, Consistency? consistency = null, string retentionPolicy = null, DateTime? timestamp = null, TimePrecision? precision = null);
public SystemTimePreciseTimestampGenerator(TimePrecision precision) { Precision = precision; }
protected string CreateUrl(string path, string database = null, string query = null, TimePrecision? timePrecision = null, Consistency? consistency = null, string retentionPolicy = null, TimePrecision? resultPrecision = null) { var queryString = new StringBuilder("?"); if (!string.IsNullOrEmpty(query)) { queryString.Append("q=" + Uri.EscapeDataString(query.StripWhitespace()) + "&"); } if (!string.IsNullOrEmpty(database)) { queryString.Append("db=" + Uri.EscapeDataString(database.FormatIdentifier()) + "&"); } if (retentionPolicy != null) { queryString.Append("rp=" + Uri.EscapeDataString(retentionPolicy.FormatIdentifier()) + "&"); } if (!string.IsNullOrEmpty(Settings.Username) && !string.IsNullOrEmpty(Settings.Password)) { queryString.Append("u=" + Uri.EscapeDataString(Settings.Username.Trim()) + "&"); queryString.Append("p=" + Uri.EscapeDataString(Settings.Password.Trim()) + "&"); } if (timePrecision.HasValue) { switch (timePrecision) { case TimePrecision.Nanosecond: // This is the default precision queryString.Append("precision=n&"); break; case TimePrecision.Microsecond: queryString.Append("precision=u&"); break; case TimePrecision.Millisecond: queryString.Append("precision=ms&"); break; case TimePrecision.Second: queryString.Append("precision=s&"); break; case TimePrecision.Minute: queryString.Append("precision=m&"); break; case TimePrecision.Hour: queryString.Append("precision=h&"); break; } } if (consistency.HasValue) { switch (consistency) { case Consistency.One: queryString.Append("consistency=one&"); break; case Consistency.Quorum: queryString.Append("consistency=quorum&"); break; case Consistency.All: queryString.Append("consistency=all&"); break; case Consistency.Any: queryString.Append("consistency=any&"); break; } } if (resultPrecision.HasValue) { switch (resultPrecision.Value) { case TimePrecision.Nanosecond: // This is the default precision queryString.Append("epoch=n&"); break; case TimePrecision.Microsecond: queryString.Append("epoch=u&"); break; case TimePrecision.Millisecond: queryString.Append("epoch=ms&"); break; case TimePrecision.Second: queryString.Append("epoch=s&"); break; case TimePrecision.Minute: queryString.Append("epoch=m&"); break; case TimePrecision.Hour: queryString.Append("epoch=h&"); break; } } if (queryString.Length > 1) { queryString.Length -= 1; } else { queryString.Length = 0; } return string.Format("{0}://{1}:{2}{3}{4}", Settings.UseHttps ? "https" : "http", Settings.Host, Settings.Port, path.StartsWith("/") ? path : "/" + path, queryString); }
private async Task <bool> PostPointsAsync(string dbName, TimePrecision precision, string retention, IEnumerable <IInfluxDatapoint> points) { Regex multiLinePattern = new Regex(@"([\P{Cc}].*?) '([\P{Cc}].*?)':([\P{Cc}].*?)\\n", RegexOptions.Compiled, TimeSpan.FromSeconds(5)); Regex oneLinePattern = new Regex(@"{\""error"":""([9\P{Cc}]+) '([\P{Cc}]+)':([a-zA-Z0-9 ]+)", RegexOptions.Compiled, TimeSpan.FromSeconds(5)); var line = new StringBuilder(); foreach (var point in points) { line.AppendFormat("{0}\n", point.ConvertToInfluxLineProtocol()); } //remove last \n line.Remove(line.Length - 1, 1); ByteArrayContent requestContent = new ByteArrayContent(Encoding.UTF8.GetBytes(line.ToString())); var endPoint = new Dictionary <string, string>() { { "db", dbName } }; if (precision > 0) { endPoint.Add("precision", precisionLiterals[(int)precision]); } if (!String.IsNullOrWhiteSpace(retention)) { endPoint.Add("rp", retention); } HttpResponseMessage response = await PostAsync(endPoint, requestContent); if (response.StatusCode == HttpStatusCode.Unauthorized || response.StatusCode == HttpStatusCode.BadGateway || (response.StatusCode == HttpStatusCode.InternalServerError && response.ReasonPhrase == "INKApi Error")) //502 Connection refused { throw new UnauthorizedAccessException("InfluxDB needs authentication. Check uname, pwd parameters"); } //if(response.StatusCode==HttpStatusCode.NotFound) else if (response.StatusCode == HttpStatusCode.BadRequest) { var content = await response.Content.ReadAsStringAsync(); //regex assumes error text from https://github.com/influxdata/influxdb/blob/master/models/points.go ParsePointsWithPrecision //fmt.Sprintf("'%s': %v", string(block[start:len(block)]) List <string> parts = null; string l = ""; if (content.Contains("partial write")) { try { if (content.Contains("\\n")) { parts = multiLinePattern.Matches(content.Substring(content.IndexOf("partial write:\\n") + 16)).ToList(); } else { parts = oneLinePattern.Matches(content.Substring(content.IndexOf("partial write:\\n") + 16)).ToList(); } if (parts.Count == 0) { throw new InfluxDBException("Partial Write", new Regex(@"\""error\"":\""(.*?)\""").Match(content).Groups[1].Value); } if (parts[1].Contains("\\n")) { l = parts[1].Substring(0, parts[1].IndexOf("\\n")).Unescape(); } else { l = parts[1].Unescape(); } } catch (InfluxDBException e) { throw e; } catch (Exception) { } var point = points.Where(p => p.ConvertToInfluxLineProtocol() == l).FirstOrDefault(); if (point != null) { throw new InfluxDBException("Partial Write", $"Partial Write : {parts?[0]} due to {parts?[2]}", point); } else { throw new InfluxDBException("Partial Write", $"Partial Write : {parts?[0]} due to {parts?[2]}", l); } } else { throw InfluxDBException.ProcessInfluxDBError(content); } } else if (response.StatusCode == HttpStatusCode.NoContent) { return(true); } else { return(false); } }
/// <summary> /// Toes the time. /// </summary> /// <param name="date">The date.</param> /// <param name="precision">The precision.</param> /// <returns></returns> public static Time ToTime(this DateTime date, TimePrecision precision) { return(new Time(date, precision)); }
/// <summary> /// Queries Influx DB and gets a time series data back. Ideal for fetching measurement values. /// The return list is of InfluxSeries, and each element in there will have properties named after columns in series /// THis uses Chunking support from InfluxDB. It returns results in streamed batches rather than as a single response /// Responses will be chunked by series or by every ChunkSize points, whichever occurs first. /// </summary> /// <param name="dbName">Name of the database</param> /// <param name="measurementQuery">Query text, Only results with single series are supported for now</param> /// <param name="ChunkSize">Maximum Number of points in a chunk</param> /// <param name="precision">epoch precision of the data set</param> /// <returns>List of InfluxSeries</returns> /// <seealso cref="InfluxSeries"/> public async Task <List <IInfluxSeries> > QueryMultiSeriesAsync(string dbName, string measurementQuery, int ChunkSize, TimePrecision precision = TimePrecision.Nanoseconds) { var response = await GetAsync(new Dictionary <string, string>() { { "db", dbName }, { "q", measurementQuery }, { "chunked", "true" }, { "chunk_size", ChunkSize.ToString() }, { "epoch", precisionLiterals[(int)precision] } }, HttpCompletionOption.ResponseHeadersRead); if (response == null) { throw new ServiceUnavailableException(); } if (response.StatusCode == HttpStatusCode.OK) { var results = new List <IInfluxSeries>(); var stream = await response.Content.ReadAsStreamAsync(); using (var reader = new StreamReader(stream)) { do { var str = await reader.ReadLineAsync(); var rawResult = JsonConvert.DeserializeObject <InfluxResponse>(str); if (rawResult?.Results[0]?.Series != null) { foreach (var series in rawResult?.Results[0]?.Series) { InfluxSeries result = GetInfluxSeries(precision, series); results.Add(result); } } if (!rawResult.Results[0].Partial) { break; } } while (!reader.EndOfStream); } return(results); } return(null); }
/// <summary> /// Queries Influx DB and gets a time series data back. Ideal for fetching measurement values. /// The return list is of InfluxSeries, and each element in there will have properties named after columns in series /// </summary> /// <param name="dbName">Name of the database</param> /// <param name="measurementQuery">Query text, Only results with single series are supported for now</param> /// <param name="precision">epoch precision of the data set</param> /// <returns>List of InfluxSeries</returns> /// <seealso cref="InfluxSeries"/> public async Task <List <IInfluxSeries> > QueryMultiSeriesAsync(string dbName, string measurementQuery, TimePrecision precision = TimePrecision.Nanoseconds) { var response = await GetAsync(new Dictionary <string, string> () { { "db", dbName }, { "q", measurementQuery }, { "epoch", precisionLiterals[(int)precision] } }); if (response.StatusCode == HttpStatusCode.OK) { var results = new List <IInfluxSeries> (); var rawResult = JsonConvert.DeserializeObject <InfluxResponse> (await response.Content.ReadAsStringAsync()); if (rawResult?.Results?.Count > 1) { throw new ArgumentException("The query is resulting in a format, which is not supported by this method yet"); } if (rawResult?.Results[0]?.Series != null) { foreach (var series in rawResult?.Results[0]?.Series) { var result = new InfluxSeries(); result.HasEntries = false; results.Add(result); result.SeriesName = series.Name; result.Tags = series.Tags; var entries = new List <dynamic> (); for (var row = 0; row < series?.Values?.Count; row++) { result.HasEntries = true; dynamic entry = new ExpandoObject(); entries.Add(entry); for (var col = 0; col < series.Columns.Count; col++) { var header = char.ToUpper(series.Columns[col][0]) + series.Columns[col].Substring(1); if (header == "Time") { ((IDictionary <string, object>)entry).Add(header, EpochHelper.FromEpoch(series.Values[row][col], precision)); } else { ((IDictionary <string, object>)entry).Add(header, series.Values[row][col]); } } } result.Entries = entries; } } return(results); } return(null); }
/// <summary> /// 获取显示时间 /// </summary> /// <param name="ts"></param> /// <param name="precision">时间精度</param> /// <param name="includeDay">是否显示天数</param> /// <returns></returns> public static string GetTimeText(this TimeSpan ts, TimePrecision precision, bool includeDay = true) { var totalMilliseconds = ts.TotalMilliseconds; if (totalMilliseconds <= 0) { return(string.Empty); } var text = new List <string>(); var totalSeconds = (int)totalMilliseconds / MILLISECONDS_OF_SECOND; var remainMilliseconds = totalMilliseconds - totalSeconds * MILLISECONDS_OF_SECOND; var totalMinutes = (int)totalSeconds / SECONDS_OF_MINUTE; var remainSeconds = totalSeconds - totalMinutes * SECONDS_OF_MINUTE; if (precision >= TimePrecision.Second) { if (remainMilliseconds > 0) { text.Add(string.Format("{0}.{1}秒", remainSeconds, remainMilliseconds)); } else if (remainSeconds > 0) { text.Add(string.Format("{0}秒", remainSeconds)); } } var totalHours = (int)totalMinutes / MINUTES_OF_HOUR; var remainMinutes = totalMinutes - totalHours * MINUTES_OF_HOUR; if (precision >= TimePrecision.Minute) { if (remainMinutes > 0) { text.Add(string.Format("{0}分", remainMinutes)); } } var totalDays = (int)totalHours / HOURS_OF_DAY; var remainHours = totalHours - totalDays * HOURS_OF_DAY; if (includeDay) { if (precision >= TimePrecision.Hour) { if (remainHours > 0) { text.Add(string.Format("{0}小时", remainHours)); } } if (precision >= TimePrecision.Day) { if (totalDays > 0) { text.Add(string.Format("{0}天", totalDays)); } } } else { if (precision >= TimePrecision.Hour) { if (totalHours > 0) { text.Add(string.Format("{0}小时", totalHours)); } } } if (text.Any()) { text.Reverse(); } return(string.Join(string.Empty, text)); }
private async Task<bool> PostPointsAsync(string dbName, TimePrecision precision, IEnumerable<IInfluxDatapoint> points) { var influxAddress = new Uri (String.Format ("{0}/write?", InfluxUrl)); var builder = new UriBuilder (influxAddress); builder.Query = await new FormUrlEncodedContent (new[] { new KeyValuePair<string, string>("db", dbName) , new KeyValuePair<string, string>("precision", precisionLiterals[(int) precision]) }).ReadAsStringAsync (); var line = new StringBuilder (); foreach ( var point in points ) line.AppendFormat ("{0}\n", point.ConvertToInfluxLineProtocol ()); //remove last \n line.Remove (line.Length - 1, 1); ByteArrayContent requestContent = new ByteArrayContent (Encoding.UTF8.GetBytes (line.ToString ())); HttpResponseMessage response = await PostAsync (builder, requestContent); if ( response.StatusCode == HttpStatusCode.Unauthorized || response.StatusCode == HttpStatusCode.BadGateway || ( response.StatusCode == HttpStatusCode.InternalServerError && response.ReasonPhrase == "INKApi Error" ) ) //502 Connection refused throw new UnauthorizedAccessException ("InfluxDB needs authentication. Check uname, pwd parameters"); //if(response.StatusCode==HttpStatusCode.NotFound) else if ( response.StatusCode == HttpStatusCode.BadRequest ) { var content = await response.Content.ReadAsStringAsync (); //regex assumes error text from https://github.com/influxdata/influxdb/blob/master/models/points.go ParsePointsWithPrecision //fmt.Sprintf("'%s': %v", string(block[start:len(block)]) List<string> parts; bool partialWrite; if ( content.Contains ("partial write") ) { if ( content.Contains ("\\n") ) parts = Regex.Matches (content.Substring (content.IndexOf ("partial write:\\n") + 16), @"([\P{Cc}].*?) '([\P{Cc}].*?)':([\P{Cc}].*?)\\n").ToList (); else parts = Regex.Matches (content.Substring (content.IndexOf ("partial write:\\n") + 16), @"([\P{Cc}].*?) '([\P{Cc}].*?)':([\P{Cc}].*?)").ToList (); partialWrite = true; } else { parts = Regex.Matches (content, @"{\""error"":""([9\P{Cc}]+) '([\P{Cc}]+)':([a-zA-Z0-9 ]+)").ToList (); partialWrite = false; } string l; if ( parts[1].Contains ("\\n") ) l = parts[1].Substring (0, parts[1].IndexOf ("\\n")).Unescape (); else l = parts[1].Unescape (); var point = points.Where (p => p.ConvertToInfluxLineProtocol () == l).FirstOrDefault (); if ( point != null ) throw new InfluxDBException (partialWrite ? "Partial Write" : "Failed to Write", String.Format ("{0}: {1} due to {2}", partialWrite ? "Partial Write" : "Failed to Write", parts[0], parts[2]), point); else throw new InfluxDBException (partialWrite ? "Partial Write" : "Failed to Write", String.Format ("{0}: {1} due to {2}", partialWrite ? "Partial Write" : "Failed to Write", parts[0], parts[2]), l); return false; } else if ( response.StatusCode == HttpStatusCode.NoContent ) return true; else return false; }
public async Task TestPostPointsAsync_DifferentPrecisions() { try { var client = new InfluxDBClient(influxUrl, dbUName, dbpwd); var time = DateTime.Now; var today = DateTime.Now.ToShortDateString(); var now = DateTime.Now.ToShortTimeString(); var points = new List <IInfluxDatapoint>(); foreach (TimePrecision precision in Enum.GetValues(typeof(TimePrecision))) { var point = new InfluxDatapoint <long>(); point.UtcTimestamp = DateTime.UtcNow; point.MeasurementName = $"Precision{precision.ToString()}"; point.Precision = precision; point.Tags.Add("Precision", precision.ToString()); point.Fields.Add("Ticks", point.UtcTimestamp.Ticks); points.Add(point); } var r = await client.PostPointsAsync(dbName, points); Assert.IsTrue(r, "PostPointsAsync retunred false"); var values = await client.QueryMultiSeriesAsync(dbName, "select * from /Precision[A-Za-z]s/"); foreach (var val in values) { var x = val?.Entries?.FirstOrDefault(); try { var d = new DateTime(long.Parse(x.Ticks)); TimeSpan t = d - x.Time; TimePrecision p = Enum.Parse(typeof(TimePrecision), x.Precision); switch (p) { case TimePrecision.Hours: Assert.IsTrue(t.TotalHours < 1); break; case TimePrecision.Minutes: Assert.IsTrue(t.TotalMinutes < 1); break; case TimePrecision.Seconds: Assert.IsTrue(t.TotalSeconds < 1); break; case TimePrecision.Milliseconds: Assert.IsTrue(t.TotalMilliseconds < 1); break; case TimePrecision.Microseconds: Assert.IsTrue(t.Ticks < (TimeSpan.TicksPerMillisecond / 1000)); break; case TimePrecision.Nanoseconds: Assert.IsTrue(t.Ticks < 1); break; } } catch (Exception e) { } } } catch (Exception e) { Assert.Fail($"Unexpected exception of type {e.GetType()} caught: {e.Message}"); return; } }
private async Task<bool> PostPointsAsync (string dbName, TimePrecision precision, string retention, IEnumerable<IInfluxDatapoint> points) { Regex multiLinePattern = new Regex (@"([\P{Cc}].*?) '([\P{Cc}].*?)':([\P{Cc}].*?)\\n", RegexOptions.Compiled, TimeSpan.FromSeconds (5)); Regex oneLinePattern = new Regex (@"{\""error"":""([9\P{Cc}]+) '([\P{Cc}]+)':([a-zA-Z0-9 ]+)", RegexOptions.Compiled, TimeSpan.FromSeconds (5)); var line = new StringBuilder (); foreach (var point in points) line.AppendFormat ("{0}\n", point.ConvertToInfluxLineProtocol ()); //remove last \n line.Remove (line.Length - 1, 1); ByteArrayContent requestContent = new ByteArrayContent (Encoding.UTF8.GetBytes (line.ToString ())); var endPoint = new Dictionary<string, string> () { { "db", dbName }, { "precision", precisionLiterals[(int)precision] } }; if (!String.IsNullOrWhiteSpace (retention)) endPoint.Add ("rp", retention); HttpResponseMessage response = await PostAsync (endPoint, requestContent); if (response.StatusCode == HttpStatusCode.Unauthorized || response.StatusCode == HttpStatusCode.BadGateway || (response.StatusCode == HttpStatusCode.InternalServerError && response.ReasonPhrase == "INKApi Error")) //502 Connection refused throw new UnauthorizedAccessException ("InfluxDB needs authentication. Check uname, pwd parameters"); //if(response.StatusCode==HttpStatusCode.NotFound) else if (response.StatusCode == HttpStatusCode.BadRequest) { var content = await response.Content.ReadAsStringAsync (); //regex assumes error text from https://github.com/influxdata/influxdb/blob/master/models/points.go ParsePointsWithPrecision //fmt.Sprintf("'%s': %v", string(block[start:len(block)]) List<string> parts = null; string l = ""; if (content.Contains ("partial write")) { try { if (content.Contains ("\\n")) parts = multiLinePattern.Matches (content.Substring (content.IndexOf ("partial write:\\n") + 16)).ToList (); else parts = oneLinePattern.Matches (content.Substring (content.IndexOf ("partial write:\\n") + 16)).ToList (); if (parts[1].Contains ("\\n")) l = parts[1].Substring (0, parts[1].IndexOf ("\\n")).Unescape (); else l = parts[1].Unescape (); } catch (Exception) { } var point = points.Where (p => p.ConvertToInfluxLineProtocol () == l).FirstOrDefault (); if (point != null) throw new InfluxDBException ("Partial Write", $"Partial Write : {parts?[0]} due to {parts?[2]}", point); else throw new InfluxDBException ("Partial Write", $"Partial Write : {parts?[0]} due to {parts?[2]}", l); } else { throw InfluxDBException.ProcessInfluxDBError (content); } } else if (response.StatusCode == HttpStatusCode.NoContent) return true; else return false; }