001/** 002 * Copyright 2013 John Ericksen 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016package org.androidtransfuse.processor; 017 018import com.google.common.collect.ImmutableMap; 019import com.google.common.collect.ImmutableSet; 020import com.sun.codemodel.JDefinedClass; 021import org.androidtransfuse.adapter.ASTType; 022import org.androidtransfuse.analysis.*; 023import org.androidtransfuse.annotations.*; 024import org.androidtransfuse.config.ScopesGeneratorWorker; 025import org.androidtransfuse.experiment.ComponentDescriptor; 026import org.androidtransfuse.gen.AnalysisGenerationFactory; 027import org.androidtransfuse.gen.ComponentsGenerator; 028import org.androidtransfuse.gen.PackageHelperGeneratorAdapter; 029import org.androidtransfuse.transaction.*; 030 031import javax.inject.Inject; 032import javax.inject.Provider; 033import java.lang.annotation.Annotation; 034import java.util.HashMap; 035import java.util.Map; 036 037/** 038 * Configures the Processor chain 039 * 040 *[ditaa] 041 * -- 042 * +---------+ +--------------+ +----------+ +-----------------+ 043 * -+->| Modules +-------+--+->| Component(s) +-+->| Manifest |---+-+-+->| Package Helpers | 044 * | +---------+ | | +--------------+ | +----------+ | | | +-----------------+ 045 * | | | | | | | 046 * | +---------------+ | | | +------------+ | | | +-----------------+ 047 * +->| ImplementedBy +-+ | +->| Components |-+ | +->| Virtual Proxies | 048 * +---------------+ | +------------+ | | +-----------------+ 049 * | | | 050 * | +-------------+ +-----------+ | | +-------------+ 051 * +->| Factory(s) +---->| Factories +----+ +->| Scopes Util | 052 * +-------------+ +-----------+ +-------------+ 053 * -- 054 * @author John Ericksen 055 */ 056public class GeneratorRepositoryProvider implements Provider<GeneratorRepository> { 057 058 private final FactoryProcessor factoryProcessor; 059 private final AnalysisGenerationFactory analysisGenerationFactory; 060 private final Provider<ActivityAnalysis> activityAnalysisProvider; 061 private final Provider<BroadcastReceiverAnalysis> broadcastReceiverAnalysisProvider; 062 private final Provider<ServiceAnalysis> serviceAnalysisProvider; 063 private final Provider<FragmentAnalysis> fragmentAnalysisProvider; 064 private final Provider<ApplicationAnalysis> applicationAnalysisProvider; 065 private final AnalysisGenerationTransactionProcessorBuilderFactory processorFactory; 066 private final GenerateModuleProcessor generateModuleProcessor; 067 private final Provider<PackageHelperGeneratorAdapter> packageHelperTransactionWorkerProvider; 068 private final ModuleProcessorBuilder moduleProcessorBuilder; 069 private final ImplementedByProcessorBuilder implementedByProcessorBuilder; 070 private final TransactionProcessorPool<Map<Provider<ASTType>, JDefinedClass>, JDefinedClass> componentsRepositoryProcessor; 071 private final Provider<ComponentsGenerator> componentsGeneratorProvider; 072 private final Provider<VirtualProxyTransactionWorker> virtualProxyTransactionWorkerProvider; 073 private final Provider<ScopesGeneratorWorker> scopesGeneratorWorkerProvider; 074 private final ScopedTransactionBuilder scopedTransactionBuilder; 075 076 @Inject 077 public GeneratorRepositoryProvider(FactoryProcessor factoryProcessor, 078 AnalysisGenerationFactory analysisGenerationFactory, 079 Provider<ActivityAnalysis> activityAnalysisProvider, 080 Provider<BroadcastReceiverAnalysis> broadcastReceiverAnalysisProvider, 081 Provider<ServiceAnalysis> serviceAnalysisProvider, 082 Provider<FragmentAnalysis> fragmentAnalysisProvider, 083 Provider<ApplicationAnalysis> applicationAnalysisProvider, 084 AnalysisGenerationTransactionProcessorBuilderFactory processorFactory, 085 GenerateModuleProcessor generateModuleProcessor, 086 Provider<PackageHelperGeneratorAdapter> packageHelperTransactionWorkerProvider, 087 ModuleProcessorBuilder moduleProcessorBuilder, 088 ImplementedByProcessorBuilder implementedByProcessorBuilder, 089 TransactionProcessorPool<Map<Provider<ASTType>, JDefinedClass>, JDefinedClass> componentsRepositoryProcessor, 090 Provider<ComponentsGenerator> componentsGeneratorProvider, 091 Provider<VirtualProxyTransactionWorker> virtualProxyTransactionWorkerProvider, 092 Provider<ScopesGeneratorWorker> scopesGeneratorWorkerProvider, 093 ScopedTransactionBuilder scopedTransactionBuilder) { 094 this.factoryProcessor = factoryProcessor; 095 this.analysisGenerationFactory = analysisGenerationFactory; 096 this.activityAnalysisProvider = activityAnalysisProvider; 097 this.broadcastReceiverAnalysisProvider = broadcastReceiverAnalysisProvider; 098 this.serviceAnalysisProvider = serviceAnalysisProvider; 099 this.fragmentAnalysisProvider = fragmentAnalysisProvider; 100 this.applicationAnalysisProvider = applicationAnalysisProvider; 101 this.processorFactory = processorFactory; 102 this.generateModuleProcessor = generateModuleProcessor; 103 this.packageHelperTransactionWorkerProvider = packageHelperTransactionWorkerProvider; 104 this.moduleProcessorBuilder = moduleProcessorBuilder; 105 this.implementedByProcessorBuilder = implementedByProcessorBuilder; 106 this.componentsRepositoryProcessor = componentsRepositoryProcessor; 107 this.componentsGeneratorProvider = componentsGeneratorProvider; 108 this.virtualProxyTransactionWorkerProvider = virtualProxyTransactionWorkerProvider; 109 this.scopesGeneratorWorkerProvider = scopesGeneratorWorkerProvider; 110 this.scopedTransactionBuilder = scopedTransactionBuilder; 111 } 112 113 @Override 114 public GeneratorRepository get() { 115 116 ImmutableMap.Builder<Class<? extends Annotation>, TransactionProcessorBuilder<Provider<ASTType>, ?>> processorMapBuilder = ImmutableMap.builder(); 117 ImmutableSet.Builder<TransactionProcessor<Provider<ASTType>, JDefinedClass>> componentProcessors = ImmutableSet.builder(); 118 119 // Module and ImplementedBy configuration processing 120 processorMapBuilder.put(TransfuseModule.class, moduleProcessorBuilder); 121 processorMapBuilder.put(ImplementedBy.class, implementedByProcessorBuilder); 122 123 TransactionProcessor<Provider<ASTType>, Void> configurationProcessors = new TransactionProcessorComposite<Provider<ASTType>, Void>( 124 ImmutableSet.of(moduleProcessorBuilder.getTransactionProcessor(), 125 implementedByProcessorBuilder.getTransactionProcessor())); 126 127 // Component processing 128 Map<Class<? extends Annotation>, Provider<? extends Analysis<ComponentDescriptor>>> analyzers = 129 new HashMap<Class<? extends Annotation>, Provider<? extends Analysis<ComponentDescriptor>>>(); 130 analyzers.put(Application.class, applicationAnalysisProvider); 131 analyzers.put(Activity.class, activityAnalysisProvider); 132 analyzers.put(BroadcastReceiver.class, broadcastReceiverAnalysisProvider); 133 analyzers.put(Service.class, serviceAnalysisProvider); 134 analyzers.put(Fragment.class, fragmentAnalysisProvider); 135 136 for (Map.Entry<Class<? extends Annotation>, Provider<? extends Analysis<ComponentDescriptor>>> providerEntry : analyzers.entrySet()) { 137 Provider<TransactionWorker<Provider<ASTType>, JDefinedClass>> workerProvider = analysisGenerationFactory.buildAnalysisGenerationProvider(providerEntry.getValue()); 138 AnalysisGenerationTransactionProcessorBuilder processorBuilder = processorFactory.buildBuilder(workerProvider); 139 140 componentProcessors.add(processorBuilder.getTransactionProcessor()); 141 142 processorMapBuilder.put(providerEntry.getKey(), processorBuilder); 143 } 144 145 TransactionProcessor<Provider<ASTType>, JDefinedClass> componentsProcessor = new TransactionProcessorComposite<Provider<ASTType>, JDefinedClass>(componentProcessors.build()); 146 147 // Manifest processing (depends on components) 148 TransactionProcessor<Void, Void> manifestProcessor = new TransactionProcessorPredefined(ImmutableSet.of(new Transaction<Void, Void>(generateModuleProcessor))); 149 TransactionProcessor<Void, Void> componentProcessorCompletion = new TransactionProcessorChain( 150 151 new TransactionProcessorChannel<Provider<ASTType>, JDefinedClass, JDefinedClass>( 152 componentsProcessor, 153 componentsRepositoryProcessor, 154 scopedTransactionBuilder.buildFactory(componentsGeneratorProvider)), 155 manifestProcessor); 156 157 ImmutableSet.Builder<TransactionProcessor<?, ?>> configurationDependentBuilders = ImmutableSet.builder(); 158 159 configurationDependentBuilders.add(componentProcessorCompletion); 160 161 processorMapBuilder.put(Factory.class, factoryProcessor); 162 163 // Package Helper processing (to be run last) 164 TransactionProcessor<Void, Void> packageHelperProcessor = new TransactionProcessorPredefined( 165 ImmutableSet.of( 166 scopedTransactionBuilder.build(packageHelperTransactionWorkerProvider), 167 scopedTransactionBuilder.build(virtualProxyTransactionWorkerProvider), 168 scopedTransactionBuilder.build(scopesGeneratorWorkerProvider))); 169 170 TransactionProcessor<?, ?> configurationDependentProcessors = 171 new TransactionProcessorComposite(configurationDependentBuilders.build()); 172 173 TransactionProcessor<Void, Void> processor = new TransactionProcessorChain(configurationProcessors, 174 new TransactionProcessorChain(factoryProcessor.getTransactionProcessor(), 175 new TransactionProcessorChain(configurationDependentProcessors, packageHelperProcessor))); 176 177 return new GeneratorRepository(processorMapBuilder.build(), processor); 178 } 179}