Repository: influxdata/influxdb-client-java (java)

Issue:
Java client: SHOW SERIES return empty result
Hi,
During implementation of tool that needs to retrieve schema of InfluxDB 2.7, I have encountered issue where `show series` return empty result, although underlying CSV contains correct data.

Data retrieved underneath as CSV is in format (note that two columns are empty!):
```
name,tags,key
,,temperature
,,pressure
```

I believe issue is in line https://github.com/influxdata/influxdb-client-java/blob/master/client/src/main/java/com/influxdb/client/internal/InfluxQLQueryApiImpl.java#L129 where last line of CSV is detected incorrectly, and instead of

```java
if (csvRecord.size() == 1 || csvRecord.get(0).equals("")) {
```
it should be
```java
if (csvRecord.size() == 1 && csvRecord.get(0).equals("")) {
```

__Steps to reproduce:__

1. Run `InfluxQLQueryResult result = client.getInfluxQLQueryApi().query(new InfluxQLQuery("SHOW SERIES", "mydb"));`
2. Observe that `result.getResults().size() == 1`, but `result.getResults().get(0).getSeries().size() == 0`

__Expected behavior:__
Object `InfluxQLQueryResult` should contain list of series retrieved from InfluxDB, as running `SHOW SERIES` from command line does it.

__Actual behavior:__
Describe What actually happened.

__Specifications:__
 - Client Version: 7.0.0
 - InfluxDB Version: 2.7.0
 - JDK Version: openjdk version "17.0.8.1" 2023-08-24
 - Platform: Linux (Arch)


Pull request description:
fix: Issue/684
Closes #684

## Proposed Changes

Fixes logic in check of marker for end of table in CSV stream.  `InfluxQLQueryApiImpl:129`

## Checklist

<!-- Checkboxes below this note can be erased if not applicable to your Pull Request. -->

- [x] CHANGELOG.md updated
- [x] Rebased/mergeable
- [x] A test has been added if appropriate
- [x] `mvn test` completes successfully
- [x] Commit messages are [conventional](https://www.conventionalcommits.org/en/v1.0.0/)
- [x] Sign [CLA](https://www.influxdata.com/legal/cla/) (if not already signed)


Patch:
diff --git a/CHANGELOG.md b/CHANGELOG.md
index b59a2b843e..e648ed0452 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,5 +1,9 @@
 ## 7.1.0 [unreleased]
 
+### Bug Fixes
+
+1, [#684](https://github.com/influxdata/influxdb-client-java/issues/684): Fix checking for CSV end of table marker when parsing CSV stream to InfluxQLQueryResult, needed for example when parsing the results of a query like "SHOW SERIES". 
+
 ### Dependencies
 
 Update dependencies:
diff --git a/client/src/main/java/com/influxdb/client/internal/InfluxQLQueryApiImpl.java b/client/src/main/java/com/influxdb/client/internal/InfluxQLQueryApiImpl.java
index f02f6d97e9..255ae17a1e 100644
--- a/client/src/main/java/com/influxdb/client/internal/InfluxQLQueryApiImpl.java
+++ b/client/src/main/java/com/influxdb/client/internal/InfluxQLQueryApiImpl.java
@@ -126,7 +126,7 @@ public class InfluxQLQueryApiImpl extends AbstractQueryApi implements InfluxQLQu
                     break;
                 }
                 int resultIndex = results.size();
-                if (csvRecord.size() == 1 || csvRecord.get(0).equals("")) {
+                if (csvRecord.size() == 1 && csvRecord.get(0).equals("")) {
                     if (series != null) {
                         InfluxQLQueryResult.Result result = new InfluxQLQueryResult.Result(
                                 resultIndex,


Test patch:
diff --git a/client/src/test/java/com/influxdb/client/internal/InfluxQLQueryApiImplTest.java b/client/src/test/java/com/influxdb/client/internal/InfluxQLQueryApiImplTest.java
index 0f7f94bf1a..fca1109ad8 100644
--- a/client/src/test/java/com/influxdb/client/internal/InfluxQLQueryApiImplTest.java
+++ b/client/src/test/java/com/influxdb/client/internal/InfluxQLQueryApiImplTest.java
@@ -25,9 +25,13 @@ import java.io.IOException;
 import java.io.StringReader;
 import java.time.Instant;
 import java.util.List;
+import java.util.Map;
 
 import com.influxdb.Cancellable;
 import com.influxdb.query.InfluxQLQueryResult;
+import org.apache.commons.csv.CSVFormat;
+import org.apache.commons.csv.CSVParser;
+import org.apache.commons.csv.CSVRecord;
 import org.assertj.core.api.Assertions;
 import org.junit.jupiter.api.Test;
 
@@ -70,7 +74,8 @@ class InfluxQLQueryApiImplTest {
 				"name,tags,time,usage_user,usage_system\n" +
 				"cpu,\"region=us-east-1,host=server1\",1483225200,13.57,1.4\n" +
 				"cpu,\"region=us-east-1,host=server1\",1483225201,14.06,1.7\n" +
-				"cpu,\"region=us-east-1,host=server2\",1483225200,67.91,1.3\n");
+				"cpu,\"region=us-east-1,host=server2\",1483225200,67.91,1.3\n"
+		);
 
 		InfluxQLQueryResult result = InfluxQLQueryApiImpl.readInfluxQLResult(reader, NO_CANCELLING, extractValues);
 
@@ -171,4 +176,43 @@ class InfluxQLQueryApiImplTest {
 							});
 				});
 	}
+
+	@Test
+	public void readInfluxQLShowSeriesRequest() throws IOException {
+
+		StringReader reader = new StringReader("name,tags,key\n" + //emulate SHOW SERIES response
+			",,temperature\n" +
+			",,\"pressure\"\n" +
+			",,humid\n" +
+			",,\"temperature,locale=nw002,device=rpi5_88e1\""
+		);
+
+		InfluxQLQueryResult result = InfluxQLQueryApiImpl.readInfluxQLResult(reader, NO_CANCELLING,
+			(columnName, rawValue, resultIndex, seriesName) -> { return rawValue;});
+
+		Assertions.assertThat(result.getResults().get(0))
+			.extracting(InfluxQLQueryResult.Result::getSeries)
+			.satisfies(series -> {
+				Assertions.assertThat(series).hasSize(1);
+				Assertions.assertThat(series.get(0))
+					.satisfies(series1 -> {
+						Assertions.assertThat(series1.getName()).isEmpty();
+						Assertions.assertThat(series1.getTags()).isEmpty();
+						Assertions.assertThat(series1.getValues()).hasSize(4);
+						Assertions.assertThat(series1.getValues())
+							.satisfies(records -> {
+								Assertions.assertThat(records.size()).isEqualTo(4);
+								Assertions.assertThat(records.get(0).getValueByKey("key"))
+									.isEqualTo("temperature");
+								Assertions.assertThat(records.get(1).getValueByKey("key"))
+									.isEqualTo("pressure");
+								Assertions.assertThat(records.get(2).getValueByKey("key"))
+									.isEqualTo("humid");
+								Assertions.assertThat(records.get(3).getValueByKey("key"))
+									.isEqualTo("temperature,locale=nw002,device=rpi5_88e1");
+							});
+					});
+			});
+
+	}
 }