1 /* 2 * Copyright (C) 2016 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.producers.internal.Producers.entryPointViewOf; 20 import static dagger.producers.internal.Producers.nonCancellationPropagatingViewOf; 21 22 import com.google.common.base.Function; 23 import com.google.common.collect.ImmutableMap; 24 import com.google.common.collect.Maps; 25 import com.google.common.util.concurrent.Futures; 26 import com.google.common.util.concurrent.ListenableFuture; 27 import dagger.producers.Producer; 28 import java.util.Map; 29 import javax.inject.Provider; 30 31 /** 32 * A {@link Producer} implementation used to implement {@link Map} bindings. This factory returns an 33 * immediate future of {@code Map<K, Producer<V>>} when calling {@link #get}. 34 */ 35 public final class MapOfProducerProducer<K, V> extends AbstractMapProducer<K, V, Producer<V>> { 36 /** Returns a new {@link Builder}. */ builder(int size)37 public static <K, V> Builder<K, V> builder(int size) { 38 return new Builder<>(size); 39 } 40 MapOfProducerProducer(ImmutableMap<K, Producer<V>> contributingMap)41 private MapOfProducerProducer(ImmutableMap<K, Producer<V>> contributingMap) { 42 super(contributingMap); 43 } 44 45 @Override compute()46 public ListenableFuture<Map<K, Producer<V>>> compute() { 47 return Futures.<Map<K, Producer<V>>>immediateFuture(contributingMap()); 48 } 49 50 /** A builder for {@link MapOfProducerProducer} */ 51 public static final class Builder<K, V> extends AbstractMapProducer.Builder<K, V, Producer<V>> { Builder(int size)52 private Builder(int size) { 53 super(size); 54 } 55 56 @Override put(K key, Producer<V> producerOfValue)57 public Builder<K, V> put(K key, Producer<V> producerOfValue) { 58 super.put(key, producerOfValue); 59 return this; 60 } 61 62 @Override put(K key, Provider<V> providerOfValue)63 public Builder<K, V> put(K key, Provider<V> providerOfValue) { 64 super.put(key, providerOfValue); 65 return this; 66 } 67 68 @Override putAll(Producer<Map<K, Producer<V>>> mapOfProducerProducer)69 public Builder<K, V> putAll(Producer<Map<K, Producer<V>>> mapOfProducerProducer) { 70 super.putAll(mapOfProducerProducer); 71 return this; 72 } 73 74 /** Returns a new {@link MapOfProducerProducer}. */ build()75 public MapOfProducerProducer<K, V> build() { 76 return new MapOfProducerProducer<>(mapBuilder.build()); 77 } 78 } 79 80 @Override newDependencyView()81 public Producer<Map<K, Producer<V>>> newDependencyView() { 82 return newTransformedValuesView(MapOfProducerProducer.<V>toDependencyView()); 83 } 84 85 @Override newEntryPointView( CancellationListener cancellationListener)86 public Producer<Map<K, Producer<V>>> newEntryPointView( 87 CancellationListener cancellationListener) { 88 return newTransformedValuesView( 89 MapOfProducerProducer.<V>toEntryPointView(cancellationListener)); 90 } 91 newTransformedValuesView( Function<Producer<V>, Producer<V>> valueTransformationFunction)92 private Producer<Map<K, Producer<V>>> newTransformedValuesView( 93 Function<Producer<V>, Producer<V>> valueTransformationFunction) { 94 return dagger.producers.Producers.<Map<K, Producer<V>>>immediateProducer( 95 ImmutableMap.copyOf(Maps.transformValues(contributingMap(), valueTransformationFunction))); 96 } 97 98 @SuppressWarnings("unchecked") toDependencyView()99 private static <T> Function<Producer<T>, Producer<T>> toDependencyView() { 100 return (Function) TO_DEPENDENCY_VIEW; 101 } 102 toEntryPointView( final CancellationListener cancellationListener)103 private static <T> Function<Producer<T>, Producer<T>> toEntryPointView( 104 final CancellationListener cancellationListener) { 105 return new Function<Producer<T>, Producer<T>>() { 106 @Override 107 public Producer<T> apply(Producer<T> input) { 108 return entryPointViewOf(input, cancellationListener); 109 } 110 }; 111 } 112 113 private static final Function<Producer<?>, Producer<?>> TO_DEPENDENCY_VIEW = 114 new Function<Producer<?>, Producer<?>>() { 115 @Override 116 public Producer<?> apply(Producer<?> input) { 117 return nonCancellationPropagatingViewOf(input); 118 } 119 }; 120 } 121