Java tutorial
/** * Axelor Business Solutions * * Copyright (C) 2015 Axelor (<http://axelor.com>). * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License, version 3, * as published by the Free Software Foundation. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Affero General Public License for more details. * * You should have received a copy of the GNU Affero General Public License * along with this program. If not, see <http://www.gnu.org/licenses/>. */ package com.axelor.apps.base.service.administration; import java.lang.reflect.Field; import org.joda.time.DateTime; import org.joda.time.Interval; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.axelor.apps.base.db.Batch; import com.axelor.apps.base.db.repo.BatchRepository; import com.axelor.apps.base.exceptions.IExceptionMessage; import com.axelor.auth.db.AuditableModel; import com.axelor.db.JPA; import com.axelor.db.Model; import com.axelor.exception.AxelorException; import com.axelor.i18n.I18n; import com.google.common.base.Preconditions; import com.google.inject.Inject; import com.google.inject.persist.Transactional; public abstract class AbstractBatch { @Inject protected GeneralService generalService; static final Logger LOG = LoggerFactory.getLogger(AbstractBatch.class); protected Batch batch; protected Model model; private int done, anomaly; @Inject protected BatchRepository batchRepo; protected AbstractBatch() { this.batch = new Batch(); this.batch.setStartDate(new DateTime()); this.done = 0; this.anomaly = 0; this.batch.setDone(this.done); this.batch.setAnomaly(this.anomaly); } public Batch getBatch() { return batch; } public Batch run(AuditableModel model) { Preconditions.checkNotNull(model); if (isRunnable(model)) { try { start(); process(); stop(); return batch; } catch (Exception e) { unarchived(); throw new RuntimeException(e); } } else { throw new RuntimeException(I18n.get(IExceptionMessage.ABSTRACT_BATCH_1)); } } abstract protected void process(); protected boolean isRunnable(Model model) { this.model = model; if (model.getArchived() != null) { return !model.getArchived(); } else { return true; } } protected void start() throws IllegalArgumentException, IllegalAccessException, AxelorException { LOG.info("Dbut batch {} ::: {}", new Object[] { model, batch.getStartDate() }); model.setArchived(true); associateModel(); checkPoint(); } /** * As {@code batch} entity can be detached from the session, call {@code Batch.find()} get the entity in the persistant context. * Warning : {@code batch} entity have to be saved before. */ protected void stop() { batch = batchRepo.find(batch.getId()); batch.setEndDate(new DateTime()); batch.setDuration(getDuring()); checkPoint(); unarchived(); LOG.info("Fin batch {} ::: {}", new Object[] { model, batch.getEndDate() }); } protected void incrementDone() { batch = batchRepo.find(batch.getId()); done += 1; batch.setDone(done); checkPoint(); LOG.debug("Done ::: {}", done); } protected void incrementAnomaly() { batch = batchRepo.find(batch.getId()); anomaly += 1; batch.setAnomaly(anomaly); checkPoint(); LOG.debug("Anomaly ::: {}", anomaly); } protected void addComment(String comment) { batch = batchRepo.find(batch.getId()); batch.setComments(comment); checkPoint(); } @Transactional protected Batch checkPoint() { return batchRepo.save(batch); } @Transactional protected void unarchived() { model = JPA.find(generalService.getPersistentClass(model), model.getId()); model.setArchived(false); } private int getDuring() { return new Interval(batch.getStartDate(), batch.getEndDate()).toDuration().toStandardSeconds() .toStandardMinutes().getMinutes(); } private void associateModel() throws IllegalArgumentException, IllegalAccessException { LOG.debug("ASSOCIATE batch:{} TO model:{}", new Object[] { batch, model }); for (Field field : batch.getClass().getDeclaredFields()) { LOG.debug("TRY TO ASSOCIATE field:{} TO model:{}", new Object[] { field.getType().getName(), model.getClass().getName() }); if (isAssociable(field)) { LOG.debug("FIELD ASSOCIATE TO MODEL"); field.setAccessible(true); field.set(batch, model); field.setAccessible(false); break; } } } private boolean isAssociable(Field field) { return field.getType().equals(generalService.getPersistentClass(model)); } }