Как сделать весеннюю сделку атомной - PullRequest
0 голосов
/ 03 января 2012

Мне нужно сохранить некоторые объекты в базе данных атомарно, но у меня возникли некоторые трудности ... У меня есть 4 объекта: Emitente, NotaFiscal, Item и Duplicata. Entity Item и Duplicata зависят от NotaFiscal, который зависит от Emitente. Итак, мои дао классы пытаются сохранить Emitente, затем NotaFiscal, затем Duplicata и наконец Item. Но когда я пытаюсь сохранить NotaFiscal, я получаю сообщение о том, что Emitente не существует. Эти же сущности были сохранены правильно с помощью entityManager.getTransaction (). Begin (); подход, когда эта программа была на рабочем столе ...

Это класс, который вызывает все классы Дао:

public class ControladorArmazenamentoNFeCompleta extends BaseDao implements
    IControladorArmazenamentoNotaFiscalCompleta {

private static final long serialVersionUID = 1L;
private IControladorArmazenamentoNFe armazenadorNFe;
private IControladorArmazenamentoElementoNFe<Item> armazenadorItem;
private IControladorArmazenamentoEmitente armazenadorEmitente;
private IControladorArmazenamentoElementoNFe<Duplicata> armazenadorDuplicata;
private String mensagemErro;

public ControladorArmazenamentoNFeCompleta(
        EntityManagerFactory entityManagerFactory) {
    super(entityManagerFactory);
}

public StatusArmazenamento criar(NotaFiscal bean) {
    if (armazenarEmitente(bean)) {
            if (armazenadorNFe.recuperarPelaChave(bean.getId()) == null) {
                if (armazenadorNFe.criar(bean)) {
                    if (armazenarDuplicatas(bean)) {
                        if (armazenarItens(bean)) {                             
                            return StatusArmazenamento.SUCESSO;
                        } else {
                            mensagemErro = armazenadorItem
                                    .getMensagemErro();
                        }
                    } else {
                        mensagemErro = armazenadorDuplicata
                                .getMensagemErro();
                    }
                } else {
                    mensagemErro = armazenadorNFe.getMensagemErro();
                }
            } else {
                mensagemErro = "A nota fiscal já foi importada!";
                return StatusArmazenamento.IMPORTADA_ANTERIORMENTE;
            }
        }
    return StatusArmazenamento.ERRO;
}

private boolean armazenarEmitente(NotaFiscal bean) {
    if (armazenadorEmitente.recuperarPeloId(bean.getEmitente()
            .getNumeroCadastroNacional()) == null) {
        if (!armazenadorEmitente.criar(bean.getEmitente())) {
            mensagemErro = armazenadorEmitente.getMensagemErro();
            return false;
        }
    }
    return true;
}

private boolean armazenarDuplicatas(NotaFiscal notaFiscal) {
    armazenadorDuplicata.setChaveNotaFiscal(notaFiscal.getId());
    Cobranca cobranca = notaFiscal.getCobranca();
    if (cobranca != null) {
        for (Duplicata duplicata : cobranca.getListaDeDuplicatas()) {
            if (!armazenadorDuplicata.criar(duplicata))
                return false;
        }
    }
    return true;
}

private boolean armazenarItens(NotaFiscal notaFiscal) {
    armazenadorItem.setChaveNotaFiscal(notaFiscal.getId());
    if (notaFiscal.getListaDeItens() == null)
        return false;
    for (Item item : notaFiscal.getListaDeItens()) {
        if (!armazenadorItem.criar(item))
            return false;
    }
    return true;
}

и это конфигурация пружины:

<bean id="transactionManager"
    class="org.springframework.transaction.jta.JtaTransactionManager" />

<tx:advice id="txDao">
    <tx:attributes>
        <tx:method name="recuperar*" read-only="true" />
        <tx:method name="criar" rollback-for="PreexistingEntityException,Exception"/>
        <tx:method name="editar"
            rollback-for="IllegalOrphanException,NonexistentEntityException,Exception"/>
    </tx:attributes>
</tx:advice>

<tx:advice id="txControlador">
    <tx:attributes>
        <tx:method name="criar" rollback-for="Exception"/>
        <tx:method name="atualizar" rollback-for="Exception"/>
    </tx:attributes>
</tx:advice>

<aop:config>
    <aop:pointcut id="operacoesDao"
        expression="execution(* com.hrgi.persistencia.dao.*.*(..))" />
    <aop:pointcut id="operacoesCadastroDao"
        expression="execution(* com.hrgi.persistencia.cadastro.dao.interfaces.*.*(..))" />
    <aop:pointcut id="operacoesBancoDao"
        expression="execution(* com.hrgi.persistencia.banco.dao.interfaces.*.*(..))" />
    <aop:pointcut id="operacoesNFeDao"
        expression="execution(* com.hrgi.persistencia.nfe.dao.interfaces.*.*(..))" />
    <aop:pointcut id="operacoesControladorArmazenamento"
        expression="execution(* com.hrgi.persistencia.*.*(..))" />
    <aop:pointcut id="operacoesControladorArmazenamentoNFe"
        expression="execution(* com.hrgi.persistencia.nfe.controladores.interfaces.*.*(..))" />

    <aop:advisor advice-ref="txDao" pointcut-ref="operacoesDao" />
    <aop:advisor advice-ref="txDao" pointcut-ref="operacoesCadastroDao" />
    <aop:advisor advice-ref="txDao" pointcut-ref="operacoesBancoDao" />
    <aop:advisor advice-ref="txDao" pointcut-ref="operacoesNFeDao" />
    <aop:advisor advice-ref="txControlador"
        pointcut-ref="operacoesControladorArmazenamento" />
    <aop:advisor advice-ref="txControlador"
        pointcut-ref="operacoesControladorArmazenamentoNFe" />
</aop:config>

что я мог сделать, чтобы решить это?

1 Ответ

0 голосов
/ 04 января 2012

Я решил проблему простым изменением распространения:

<tx:advice id="txDao">
    <tx:attributes>
        <tx:method name="recuperar*" read-only="true" />
        <tx:method name="criar" rollback-for="PreexistingEntityException,Exception"
            propagation="REQUIRED" />
        <tx:method name="editar"
            rollback-for="IllegalOrphanException,NonexistentEntityException,Exception"
            propagation="REQUIRED" />
    </tx:attributes>
</tx:advice>

<tx:advice id="txControlador">
    <tx:attributes>
        <tx:method name="criar" rollback-for="Exception"
            propagation="REQUIRES_NEW" />
        <tx:method name="atualizar" rollback-for="Exception"
            propagation="REQUIRES_NEW" />
    </tx:attributes>
</tx:advice>

Спасибо за ваше внимание.

...