influxdata / influxdata/influxdb-java

The client act in a synchronous manner when BatchProcessorr#queue is full.

Ouverte
#688 7 commentaires 0 réactions 0 personnes assignées Voir sur GitHub

Personne n'a encore pris cette issue.

Langage dominant
Java
Étoiles
1.2k
Forks
469
Métriques de merge des PR
Aucune PR mergée en 30 j

Description

I went through the BatchProcessor implementation and noticed that when the batch processor is lagging behind and is not able to clear the queue, InfluxDB.write(Point p) becomes a blocking call even when one has configured it to write in an asynchronous manner.
This is happening because the queue instance is of type LinkedBlockingQueue and put(E e) is used for enqueueing which blocks the thread trying to enqueue.
IMO, this behaviour is very misleading, can block all the application threads who are trying to write whenever the write latencies on the influx-db server increases.
I am using the influxdb-java:2.15
Below is the sample Junit test to simulate this.



import okhttp3.Interceptor;
import okhttp3.OkHttpClient;
import okhttp3.Response;
import org.influxdb.BatchOptions;
import org.influxdb.InfluxDB;
import org.influxdb.InfluxDBFactory;
import org.influxdb.dto.Point;
import org.influxdb.dto.Query;
import org.junit.Test;

import java.io.IOException;

public class InfluxTest {


    InfluxDB influxDB;

    @Test
    public void testConnection() {

        connect();

        for (int i=0;i<5000; ++i) {

            long before = System.currentTimeMillis();
            influxDB.write(Point.measurement("test").addField("a-field", 0).build());
            long after = System.currentTimeMillis();
            System.out.println(String.format("Time taken for writing %d times was %d", i, after-before));
        }

    }

    private void connect() {

            String influxDbConnectionURL = "http://localhost:8086";

            influxDB = InfluxDBFactory.connect(influxDbConnectionURL, new OkHttpClient.Builder().addInterceptor(new Interceptor() {
                @Override
                public Response intercept(Chain chain) throws IOException {
                    try {
                        Thread.sleep(10000);
                        System.out.println("interacted with influx");
                    } catch (InterruptedException e) {
                        throw new RuntimeException(e);
                    }
                    return chain.proceed(chain.request());
                }
            }));

            influxDB.query(new Query("CREATE DATABASE " + '"' + "test" + '"'));
            influxDB.setDatabase("test");

            influxDB.enableBatch(BatchOptions.DEFAULTS.exceptionHandler(
                (failedPoints, throwable) -> {
                })
            );

    }

}



The default batch size is 1000, so the 2000th write call will be blocked for ~10000ms.

Guide de contribution

Aucun guide de contribution indexé pour ce dépôt

Par où commencer

  1. Lisez l'issue en entier, puis le guide de contribution du projet.
  2. Signalez en commentaire que vous la prenez — cela évite que deux personnes fassent le même travail.
  3. Forkez le dépôt et travaillez sur une branche.
  4. Ouvrez une pull request qui référence le numéro de l'issue.

Piste de recherche

Commencez par le chemin de mise en file d’attente de BatchProcessor décrit dans l’issue et reproduisez le comportement à l’aide de l’exemple JUnit fourni avec BatchOptions et un intercepteur OkHttp retardé. Vérifiez le comportement autour de la taille de batch par défaut, en particulier lors de la 2000e écriture, et considérez l’issue comme terminée lorsque les écritures asynchrones ne bloquent plus tant que la file d’attente est pleine.

Rédigé par le modèle d'indexation à partir du texte de l'issue.

Évaluation

Stack technique
java
Domaine
backend-api-design
Type d'issue
Bug
Difficulté
3/5
Temps estimé
1-2 jours
Activité
À l'abandon
Clarté
Clairement spécifiée
Accessibilité débutants
35/100

Recevez les nouvelles issues par e-mail

Un résumé court des issues GitHub adaptées aux débutants.