package detective.core.distribute; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import groovy.lang.Script; import detective.core.Story; import detective.core.filter.FilterChainFactory; import detective.core.filter.RunnerFilter; import detective.core.filter.RunnerFilterChain; import detective.core.filter.impl.RunnerFilterChainImpl; import detective.core.runner.DslBuilderAndRun; public class JobRunnerFilterImpl implements JobRunner { class StoryFilterChainAdapter implements RunnerFilterChain<Story>{ private final JobToRun job; private final RunnerFilterChain<JobStoryRunContext> jobStoryChain; private final RunnerFilterChain<Story> internalChain; private int storyPositionIndex = -1; public StoryFilterChainAdapter(JobToRun job, RunnerFilterChain<JobStoryRunContext> chain){ this.job = job; this.jobStoryChain = chain; this.internalChain = new RunnerFilterChainImpl<Story>(createFilters()); } private List<RunnerFilter<Story>> createFilters(){ List<RunnerFilter<Story>> filters = new ArrayList<RunnerFilter<Story>>(); filters.add(new RunnerFilter<Story>(){ @Override public void doFilter(Story t, RunnerFilterChain<Story> chain) { JobStoryRunContext context = new JobStoryRunContext(); context.setStory(t); context.setJob(job); context.setCurrentStoryIndex(increaseStoryPositionAndGet()); context.setScriptClassName(job.getStoryClassName()); jobStoryChain.doFilter(context); }}); return filters; } private int increaseStoryPositionAndGet(){ storyPositionIndex ++ ; return storyPositionIndex; } @Override public Iterator<RunnerFilter<Story>> iterator() { return this.internalChain.iterator(); } @Override public void doFilter(Story t) { this.internalChain.doFilter(t); } @Override public void resetChainPosition() { this.internalChain.resetChainPosition(); } } @Override public void run(JobToRun job) { RunnerFilterChain<JobStoryRunContext> chain = createFilterChain(); StoryFilterChainAdapter adapter = new StoryFilterChainAdapter(job, chain); DslBuilderAndRun.setFilterChainCurrentThread(adapter); try { Class<?> clazz = Class.forName(job.getStoryClassName()); if (! (clazz.getSuperclass().getName().equals("groovy.lang.Script"))){ throw new RuntimeException(job.getStoryClassName() + " is not a groovy script"); } Script script = (Script)clazz.newInstance(); script.run(); } catch (Exception e) { throw new RuntimeException(e); } } @SuppressWarnings("unchecked") private RunnerFilterChain<JobStoryRunContext> createFilterChain(){ try { //default detective.core.distribute.SparkJobRunnerFilterChainFactory FilterChainFactory factory = FilterChainFactory.ConfigReader.instanceFromConfigFile("runner.spark_running.filter_chain_factory"); return (RunnerFilterChain<JobStoryRunContext>)factory.getChain(); } catch (Exception e) { throw new RuntimeException(e); } } }