ZOFTINO.COM

Dagger Multibinding

Multibinding is all about injecting collection of objects of a particular type into target or dependent object. Dagger supports multibinding, meaning if any of your classes need a set of objects of a particular type, dependency injection for that can be done using dagger.

With multibindings, you don’t need to deal with individual bindings when there is a dependency on collection of objects. Dagger takes care of collecting objects of a particular type and injecting the collection into dependent object.

In this article, I’ll show how to use multibinding with an example. You can read dependency injection using dagger to know about dagger and how use it in your project.

Dagger Multibinding Types

Dagger supports multibinding for two types of collections, set and map.

Dagger Set Multibinding

For set multibinding, you need to use IntoSet annotation on provides method so that dagger will add the object to set and inject it wherever set dependency of that type exists. In the below example, provides-methods are annotated with IntoSet, dagger will create a set of Payment type objects and inject it wherever dependency of Set exists.

 @Module
public abstract class OrderModule {
    @Binds
    @IntoSet
    public abstract Payment provideCCPayment(CreditCardPayment ccp);
    @Binds
    @IntoSet
    public abstract Payment provideDCPayment(DebitCardPayment dcp);
} 

Set dependency

    @Inject
    Set<Payment> paymentModes;

Dagger Map Multibinding

For map multibindings, you need to use IntoMap annotation and specify map key by using map key annotation. In the below example, dagger creates Map object, it uses StringKey annotation to pair string key with Taxer object. Dagger provides other key annotations such as ClassKey, IntKey, and LongKey. If you need to use class as key, you can use ClassKey annotation.

 @Binds
@IntoMap
@StringKey("east")
public abstract Taxer provideETaxer(EastZoneTaxer ezt);

@Binds
@IntoMap
@StringKey("central")
public abstract Taxer provideCTaxer(CentralZoneTaxer czt);
 

Map dependency

 @Inject
Map<String, Taxer> taxers;
 

Dagger Multibinding Example

I’ll show how to use dagger multibindings using ecommerce app’s tax calculation and payment screen. Since the focus is only on dagger multibinding, the example doesn’t contain details. To show map multibinding, I’ll use tax calculation. Let’s say, tax calculation depends on location and Taxer objects exist for each location. Dagger will collect Taxer objects into Map. Depending on the user location, Taxer object will be picked from map using location key and tax will be calculated. Similarly, to show how to use set multibinding, we will use payment selection. Depending on the payment type, payment object will be chosen from set of payment objects to process payment.

You can view or download complete example from github at https://github.com/srinurp/DaggerMultibinding

 package com.zoftino.daggermultibinding.viewmodel;

import com.zoftino.daggermultibinding.business.Payment;
import com.zoftino.daggermultibinding.business.Taxer;

import java.util.ArrayList;
import java.util.Map;
import java.util.Set;

import javax.inject.Inject;

public class PaymentTaxViewModel {

    @Inject
    Set<Payment> paymentModes;
    @Inject
    Map<String, Taxer> taxers;

    @Inject
    public PaymentTaxViewModel(){}


    public double calculateTax(double price, String taxZone){
        return taxers.get(taxZone).calculateTax(price);
    }

    public String payOrderAmount(String orderId, int paymentType){
       return (new ArrayList<Payment>(paymentModes)).get(paymentType).payOrder(orderId);
    }
}
 

Dagger module

 package com.zoftino.daggermultibinding.di;

import com.zoftino.daggermultibinding.business.CentralZoneTaxer;
import com.zoftino.daggermultibinding.business.CreditCardPayment;
import com.zoftino.daggermultibinding.business.DebitCardPayment;
import com.zoftino.daggermultibinding.business.EastZoneTaxer;
import com.zoftino.daggermultibinding.business.PayPalPayment;
import com.zoftino.daggermultibinding.business.Payment;
import com.zoftino.daggermultibinding.business.Taxer;
import com.zoftino.daggermultibinding.business.WestZoneTaxer;

import dagger.Binds;
import dagger.Module;
import dagger.multibindings.IntoMap;
import dagger.multibindings.IntoSet;
import dagger.multibindings.StringKey;

@Module
public abstract class OrderModule {
    @Binds
    @IntoSet
    public abstract Payment provideCCPayment(CreditCardPayment ccp);
    @Binds
    @IntoSet
    public abstract Payment provideDCPayment(DebitCardPayment dcp);
    @Binds
    @IntoSet
    public abstract Payment providePPPayment(PayPalPayment ppp);

    @Binds
    @IntoMap
    @StringKey("east")
    public abstract Taxer provideETaxer(EastZoneTaxer ezt);

    @Binds
    @IntoMap
    @StringKey("central")
    public abstract Taxer provideCTaxer(CentralZoneTaxer czt);

    @Binds
    @IntoMap
    @StringKey("west")
    public abstract Taxer provideWTaxer(WestZoneTaxer wzt);


}