/*
 * Copyright 2018 Google LLC
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     https://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.google.android.gnd.rx;

import android.util.Log;
import com.akaita.java.rxjava2debug.RxJava2Debug;
import io.reactivex.Completable;
import io.reactivex.CompletableConverter;
import io.reactivex.Flowable;
import io.reactivex.FlowableConverter;
import io.reactivex.Maybe;
import io.reactivex.MaybeConverter;
import io.reactivex.disposables.Disposable;
import org.reactivestreams.Subscription;

public abstract class RxDebug {
  private static final String TAG = RxDebug.class.getSimpleName();
  private static final String RX_TRACE_PREFIX = "[RxDebug]";

  /** Container for static helper methods. Do not instantiate. */
  private RxDebug() {}

  public static void logEnhancedStackTrace(Throwable t) {
    Log.e(TAG, "Unhandled Rx error", RxJava2Debug.getEnhancedStackTrace(t));
  }

  public static <T> MaybeConverter<T, Maybe<T>> traceMaybe(String tag, String streamName) {
    Tracer t = new Tracer(tag, streamName);
    return m ->
        m.doOnSubscribe(t::onSubscribe)
            .doOnSuccess(t::onSuccess)
            .doOnComplete(t::onComplete)
            .doOnError(t::onError);
  }

  public static <T> FlowableConverter<T, Flowable<T>> traceFlowable(String tag, String streamName) {
    Tracer t = new Tracer(tag, streamName);
    return f ->
        f.doOnSubscribe(t::onSubscribe)
            .doOnNext(t::onNext)
            .doOnComplete(t::onComplete)
            .doOnError(t::onError);
  }

  public static CompletableConverter<Completable> traceCompletable(
      String tag, String streamName) {
    Tracer t = new Tracer(tag, streamName);
    return c -> c.doOnSubscribe(t::onSubscribe).doOnComplete(t::onComplete).doOnError(t::onError);
  }

  private static class Tracer {
    private final String tag;
    private final String streamName;

    private Tracer(String tag, String streamName) {
      this.tag = tag;
      this.streamName = streamName;
    }

    private static void trace(String tag, String streamName, String action) {
      Log.v(tag, RX_TRACE_PREFIX + " " + streamName + " " + action);
    }

    private void onSubscribe(Disposable disposable) {
      trace(tag, streamName, "subscribe");
    }

    public void onSubscribe(Subscription subscription) {
      trace(tag, streamName, "subscribe");
    }

    public void onSuccess(Object value) {
      trace(tag, streamName, "success: " + value);
    }

    public void onNext(Object value) {
      trace(tag, streamName, "next: " + value);
    }

    public void onComplete() {
      trace(tag, streamName, "complete");
    }

    public void onError(Throwable t) {
      trace(tag, streamName, "error:  " + t);
    }
  }
}

@@ -1376,32 +1376,158 @@
 Trace(t));%0A  %7D%0A%0A
+  /**%0A   * Returns a converter for use with %7B@link Maybe#as%7D that logs all events that occur on the source%0A   * stream.%0A   */%0A
   public static 
@@ -1563,16 +1563,17 @@
 %3E%3E trace
+d
 Maybe(St
@@ -1816,32 +1816,161 @@
 :onError);%0A  %7D%0A%0A
+  /**%0A   * Returns a converter for use with %7B@link Flowable#as%7D that logs all events that occur on the%0A   * source stream.%0A   */%0A
   public static 
@@ -2012,16 +2012,17 @@
 %3E%3E trace
+d
 Flowable
@@ -2022,16 +2022,23 @@
 lowable(
+%0A      
 String t
@@ -2277,16 +2277,148 @@
 );%0A  %7D%0A%0A
+  /**%0A   * Returns a converter for use with %7B@link Completable#as%7D that logs all events that occur on the%0A   * source stream.%0A   */%0A
   public
@@ -2464,16 +2464,17 @@
 e%3E trace
+d
 Completa
@@ -2473,31 +2473,24 @@
 Completable(
-%0A      
 String tag, 
@@ -3130,37 +3130,38 @@
 %22);%0A    %7D%0A%0A    p
-ublic
+rivate
  void onSubscrib
@@ -3238,37 +3238,38 @@
 %22);%0A    %7D%0A%0A    p
-ublic
+rivate
  void onSuccess(
@@ -3339,37 +3339,38 @@
 e);%0A    %7D%0A%0A    p
-ublic
+rivate
  void onNext(Obj
@@ -3434,37 +3434,38 @@
 e);%0A    %7D%0A%0A    p
-ublic
+rivate
  void onComplete
@@ -3523,21 +3523,22 @@
 %7D%0A%0A    p
-ublic
+rivate
  void on

Add Javadoc and fix names