Home | History | Annotate | Download | only in injection
      1 /*
      2  * Copyright (c) 2007 Mockito contributors
      3  * This program is made available under the terms of the MIT License.
      4  */
      5 
      6 package org.mockito.internal.configuration.injection;
      7 
      8 import java.lang.reflect.Field;
      9 import java.util.Set;
     10 
     11 /**
     12  * Injector strategy contract
     13  */
     14 public abstract class MockInjectionStrategy {
     15 
     16     /**
     17      * NOP Strategy that will always try the next strategy.
     18      */
     19     public static MockInjectionStrategy nop() {
     20         return new MockInjectionStrategy() {
     21             protected boolean processInjection(Field field, Object fieldOwner, Set<Object> mockCandidates) {
     22                 return false;
     23             }
     24         };
     25     }
     26 
     27 
     28     private MockInjectionStrategy nextStrategy;
     29 
     30     /**
     31      * Enqueue next injection strategy.
     32      *
     33      * <p>
     34      * The implementation should take care of the actual calling if required.
     35      * </p>
     36      *
     37      * @param strategy Queued strategy.
     38      * @return The passed strategy instance to allow chaining.
     39      */
     40     public MockInjectionStrategy thenTry(MockInjectionStrategy strategy) {
     41         if(nextStrategy != null) {
     42             nextStrategy.thenTry(strategy);
     43         } else {
     44             nextStrategy = strategy;
     45         }
     46         return strategy;
     47     }
     48 
     49     /**
     50      * Actually inject mockCandidates on field.
     51      *
     52      * <p>
     53      * Actual algorithm is defined in the implementations of {@link #processInjection(Field, Object, Set)}.
     54      * However if injection occurred successfully, the process should return <code>true</code>,
     55      * and <code>false</code> otherwise.
     56      * </p>
     57      *
     58      * <p>
     59      * The code takes care of calling the next strategy if available and if of course if required
     60      * </p>
     61      *
     62      * @param onField Field needing injection.
     63      * @param fieldOwnedBy The owning instance of the field.
     64      * @param mockCandidates A set of mock candidate, that might be injected.
     65      * @return <code>true</code> if successful, <code>false</code> otherwise.
     66      */
     67     public boolean process(Field onField, Object fieldOwnedBy, Set<Object> mockCandidates) {
     68         if(processInjection(onField, fieldOwnedBy, mockCandidates)) {
     69             return true;
     70         }
     71         return relayProcessToNextStrategy(onField, fieldOwnedBy, mockCandidates);
     72     }
     73 
     74     /**
     75      * Process actual injection.
     76      *
     77      * <p>
     78      * Don't call this method directly, instead call {@link #process(Field, Object, Set)}
     79      * </p>
     80      *
     81      * @param field Field needing injection
     82      * @param fieldOwner Field owner instance.
     83      * @param mockCandidates Pool of mocks to inject.
     84      * @return <code>true</code> if injection occurred, <code>false</code> otherwise
     85      */
     86     protected abstract boolean processInjection(Field field, Object fieldOwner, Set<Object> mockCandidates);
     87 
     88     private boolean relayProcessToNextStrategy(Field field, Object fieldOwner, Set<Object> mockCandidates) {
     89         return nextStrategy != null && nextStrategy.process(field, fieldOwner, mockCandidates);
     90     }
     91 }
     92