diff --git a/CHANGELOG.md b/CHANGELOG.md index 55556b46b..b7c77d5ce 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,6 +3,9 @@ ### Features 1. [#101](https://github.com/influxdata/influxdb-client-csharp/pull/304): Add `InvocableScriptsApi` to create, update, list, delete and invoke scripts by seamless way +### Bug Fixes +1. [#309](https://github.com/influxdata/influxdb-client-csharp/pull/309): Query expression for joins of binary operators [LINQ] + ## 4.0.0 [2022-03-18] :warning: The underlying `RestSharp` library was updated the latest major version `v107`. The new version of `RestSharp` switched from the legacy `HttpWebRequest` class to the standard well-known `System.Net.Http.HttpClient` instead. This improves performance and solves lots of issues, like hanging connections, updated protocols support, and many other problems. diff --git a/Client.Linq.Test/InfluxDBQueryVisitorTest.cs b/Client.Linq.Test/InfluxDBQueryVisitorTest.cs index 1f772c002..94f2dca12 100644 --- a/Client.Linq.Test/InfluxDBQueryVisitorTest.cs +++ b/Client.Linq.Test/InfluxDBQueryVisitorTest.cs @@ -1070,6 +1070,30 @@ public void AlignFieldsWithPivot() } } + [Test] + public void FilterByTimeAndTagWithAnds() + { + var start = new DateTime(2019, 11, 16, 8, 20, 15, DateTimeKind.Utc); + var stop = new DateTime(2021, 01, 10, 5, 10, 0, DateTimeKind.Utc); + + var query = from s in InfluxDBQueryable.Queryable("my-bucket", "my-org", _queryApi) + where s.Timestamp >= start && s.Timestamp < stop && s.SensorId == "id-1" + select s; + var visitor = BuildQueryVisitor(query); + + const string expected = "start_shifted = int(v: time(v: p3))\n" + + "stop_shifted = int(v: time(v: p4))\n\n" + + "from(bucket: p1) " + + "|> range(start: time(v: start_shifted), stop: time(v: stop_shifted)) " + + "|> filter(fn: (r) => (r[\"sensor_id\"] == p5)) " + + "|> pivot(rowKey:[\"_time\"], columnKey: [\"_field\"], valueColumn: \"_value\") " + + "|> drop(columns: [\"_start\", \"_stop\", \"_measurement\"])"; + + Console.WriteLine(visitor.BuildFluxQuery()); + + Assert.AreEqual(expected, visitor.BuildFluxQuery()); + } + private InfluxDBQueryVisitor BuildQueryVisitor(IQueryable queryable, Expression expression = null) { var queryExecutor = (InfluxDBQueryExecutor)((DefaultQueryProvider)queryable.Provider).Executor; diff --git a/Client.Linq/Internal/QueryExpressionTreeVisitor.cs b/Client.Linq/Internal/QueryExpressionTreeVisitor.cs index 1e3354f14..d1f7816b4 100644 --- a/Client.Linq/Internal/QueryExpressionTreeVisitor.cs +++ b/Client.Linq/Internal/QueryExpressionTreeVisitor.cs @@ -396,6 +396,7 @@ internal static void NormalizeExpressions(List parts) .ToList(); foreach (var index in indexes) + { // () if (parts.Count > index + 1 && parts[index + 1] is RightParenthesis) { @@ -406,6 +407,16 @@ internal static void NormalizeExpressions(List parts) return; } + // ( + if (parts.Count == 1 && parts[index] is LeftParenthesis) + { + parts.RemoveAt(index); + + NormalizeExpressions(parts); + return; + } + } + // (( )) if (parts.Count >= 4 && parts[0] is LeftParenthesis && parts[1] is LeftParenthesis && parts[parts.Count - 2] is RightParenthesis && parts[parts.Count - 1] is RightParenthesis)