1 /* 2 * Copyright (C) 2018 The Dagger Authors. 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package dagger.producers.internal; 18 19 import static dagger.internal.Preconditions.checkNotNull; 20 21 import com.google.common.util.concurrent.ListenableFuture; 22 import dagger.internal.DoubleCheck; 23 import dagger.producers.Producer; 24 import javax.inject.Provider; 25 26 /** 27 * A DelegateProducer that is used to stitch Producer indirection during initialization across 28 * partial subcomponent implementations. 29 */ 30 public final class DelegateProducer<T> implements CancellableProducer<T> { 31 private CancellableProducer<T> delegate; 32 33 @Override get()34 public ListenableFuture<T> get() { 35 return delegate.get(); 36 } 37 38 // TODO(ronshapiro): remove this once we can reasonably expect generated code is no longer using 39 // this method 40 @Deprecated setDelegatedProducer(Producer<T> delegate)41 public void setDelegatedProducer(Producer<T> delegate) { 42 setDelegate(this, delegate); 43 } 44 45 /** 46 * Sets {@code delegateProducer}'s delegate producer to {@code delegate}. 47 * 48 * <p>{@code delegateProducer} must be an instance of {@link DelegateProducer}, otherwise this 49 * method will throw a {@link ClassCastException}. 50 */ setDelegate(Producer<T> delegateProducer, Producer<T> delegate)51 public static <T> void setDelegate(Producer<T> delegateProducer, Producer<T> delegate) { 52 checkNotNull(delegate); 53 DelegateProducer<T> asDelegateProducer = (DelegateProducer<T>) delegateProducer; 54 if (asDelegateProducer.delegate != null) { 55 throw new IllegalStateException(); 56 } 57 asDelegateProducer.delegate = (CancellableProducer<T>) delegate; 58 } 59 60 /** 61 * Returns the factory's delegate. 62 * 63 * @throws NullPointerException if the delegate has not been set 64 */ getDelegate()65 CancellableProducer<T> getDelegate() { 66 return checkNotNull(delegate); 67 } 68 69 @Override cancel(boolean mayInterruptIfRunning)70 public void cancel(boolean mayInterruptIfRunning) { 71 delegate.cancel(mayInterruptIfRunning); 72 } 73 74 @Override newDependencyView()75 public Producer<T> newDependencyView() { 76 return new ProducerView<T>() { 77 @Override 78 Producer<T> createDelegate() { 79 return delegate.newDependencyView(); 80 } 81 }; 82 } 83 84 @Override 85 public Producer<T> newEntryPointView(final CancellationListener cancellationListener) { 86 return new ProducerView<T>() { 87 @Override 88 Producer<T> createDelegate() { 89 return delegate.newEntryPointView(cancellationListener); 90 } 91 }; 92 } 93 94 private abstract static class ProducerView<T> implements Producer<T> { 95 private final Provider<Producer<T>> delegate = 96 DoubleCheck.provider( 97 new Provider<Producer<T>>() { 98 @Override 99 public Producer<T> get() { 100 return createDelegate(); 101 } 102 }); 103 104 abstract Producer<T> createDelegate(); 105 106 @Override 107 public ListenableFuture<T> get() { 108 return delegate.get().get(); 109 } 110 } 111 } 112