package com.ga.batch.config;

import com.ga.batch.settlement.SettlementContext;
import org.springframework.batch.core.Job;
import org.springframework.batch.core.Step;
import org.springframework.batch.core.configuration.annotation.JobScope;
import org.springframework.batch.core.job.builder.JobBuilder;
import org.springframework.batch.core.repository.JobRepository;
import org.springframework.batch.core.step.builder.StepBuilder;
import org.springframework.batch.core.step.tasklet.Tasklet;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.transaction.PlatformTransactionManager;

import com.ga.batch.settlement.step.*;

@Configuration
public class BatchConfig {

    @Bean
    @JobScope
    public SettlementContext settlementContext(@Value("#{jobParameters['settleMonth']}") String settleMonth,
                                                @Value("#{jobParameters['jobLogId'] ?: -1L}") Long jobLogId) {
        SettlementContext ctx = new SettlementContext();
        ctx.setSettleMonth(settleMonth);
        ctx.setJobLogId(jobLogId);
        return ctx;
    }

    @Bean
    public Job monthlySettlementJob(JobRepository jobRepository,
                                    PlatformTransactionManager tx,
                                    ReceiveDataStep step1,
                                    TransformDataStep step2,
                                    ReconcileStep step3,
                                    CalcRecruitStep step4,
                                    CalcMaintainStep step5,
                                    ChargebackExceptionStep step6,
                                    CalcOverrideStep step7,
                                    AggregateStep step8,
                                    AccountingEntryGenerateStep step9,
                                    YearEndIncomeAggregateStep step10,
                                    WithholdingTaxQuarterlyStep step11,
                                    VatReportQuarterlyStep step12) {
        return new JobBuilder("MONTHLY_SETTLEMENT", jobRepository)
                .start(taskletStep("receiveData",                step1,  jobRepository, tx))
                .next(taskletStep("transformData",               step2,  jobRepository, tx))
                .next(taskletStep("reconcile",                   step3,  jobRepository, tx))
                .next(taskletStep("calcRecruit",                 step4,  jobRepository, tx))
                .next(taskletStep("calcMaintain",                step5,  jobRepository, tx))
                .next(taskletStep("chargebackException",         step6,  jobRepository, tx))
                .next(taskletStep("calcOverride",                step7,  jobRepository, tx))
                .next(taskletStep("aggregate",                   step8,  jobRepository, tx))
                .next(taskletStep("accountingEntryGenerate",     step9,  jobRepository, tx))
                .next(taskletStep("yearEndIncomeAggregate",      step10, jobRepository, tx))
                .next(taskletStep("withholdingTaxQuarterly",     step11, jobRepository, tx))
                .next(taskletStep("vatReportQuarterly",          step12, jobRepository, tx))
                .build();
    }

    private Step taskletStep(String name, Tasklet tasklet,
                             JobRepository jobRepository, PlatformTransactionManager tx) {
        return new StepBuilder(name, jobRepository)
                .tasklet(tasklet, tx)
                .build();
    }
}
