Squeak.ru - шаблоны программирования

Как мне внедрить зависимости в неизменяемые объекты домена, созданные Mybatis?

Я разрабатываю приложение Spring Boot и использую Mybatis. Чтобы гарантировать неизменность объектов, созданных Mybatis, я заставляю Mybatis использовать <constructor> вместо сеттеров, которые делают объекты изменяемыми. Как и другие порядковые объекты, эти объекты, созданные Mybatis, нуждаются в зависимостях для выполнения своих обязанностей, и эти зависимости иногда представляют собой bean-компоненты, экземпляры которых создаются Spring.

Если объект создается Spring, к нему легко внедрить зависимости. Но объект, созданный Mybatis, очевидно, находится вне контейнера DI Spring, и вы не можете использовать @Autowired или другую механику Spring для внедрения его зависимостей.

Конечно, я могу вводить зависимости вручную после создания Mybatis, например:

DomainA d = DomainAMapper.fetchOne();
d.setDependency(dependency);

Но это нарушает неизменность DomainA.

Как я могу удовлетворить свою потребность, то есть внедрить зависимости в объекты, созданные Mybatis, сохраняя при этом их неизменность?


  • Можете ли вы поделиться теми же примерами зависимостей, которыми вы хотели бы управлять? Например, назовите мне несколько зависимостей в DomainA. 28.09.2017
  • @Rafa Спасибо за комментарий. Я имею в виду зависимости здесь, как и другие классы, используемые в классе DomainA. В моей текущей ситуации это класс-оболочка Java нативного модуля, написанный на C++ для работы с машинным обучением. Я хотел бы ввести его, чтобы упростить модульное тестирование. 28.09.2017

Ответы:


1

Если вас устраивает текущий дизайн и вы сосредоточены на тестировании, тогда PowerMockit должен удовлетворить ваши потребности, поскольку он способен «устанавливать/издеваться» над частными членами.

Пример:

@Component
public class DomainA {
    @Autowired
    private ApplicationContext context;
    public boolean isContextInitilized() {
        return context != null;
    }
}

import org.powermock.api.support.membermodification.MemberModifier;
...    
@RunWith(SpringRunner.class)
@SpringBootTest
public class DemoApplicationTests {
    @Autowired
    ApplicationContext contextToInject;
    @Autowired
    DomainA domainAAutowired;

    @Test
    public void contextLoads() throws IllegalArgumentException, IllegalAccessException {
        // Autowired spring beans work fine
        assertTrue(domainAAutowired.isContextInitilized());
        // Class out of spring context won't initialize dependencies
        DomainA domainOutOfSpringContext = new DomainA();
        assertFalse(domainOutOfSpringContext.isContextInitilized());
        // We can 'set' private members using PowerMock
        MemberModifier.field(DomainA.class, "context").set(domainOutOfSpringContext, contextToInject);
        assertTrue(domainOutOfSpringContext.isContextInitilized());
    }
}

Кстати, классы MyBatis должны быть простыми POJO. Наличие весенних зависимостей в MyBatis может быть индикатором плохого разделения задач, поскольку они должны касаться только уровня сохраняемости.

28.09.2017
  • Большое спасибо за ответ. И ваше мнение, что Having spring dependencies in MyBatis may be an indicator of poor separation of concerns as they should be only concerned with the persistence layer действительно имеет для меня смысл. Но в этом смысле должны ли сгенерированные Mybatis объекты иметь только геттеры и сеттеры и делегировать логику другим классам? У вас есть идеи, как избежать анемичной модели домена? 04.10.2017
  • Представьте, что интерфейсы MyBatis — это Repositories, а классы MyBatis — как Entities. Затем создайте слой Service, который является более естественным местом для хранения пружинных зависимостей. Слой Service должен быть тонким, но способным делегировать другим ресурсам. Вы также можете представить слой Service как слой Facade для ваших ресурсов. 04.10.2017
  • Еще раз спасибо за ответ. The Service layer should be thin but capable to delegate to other resources. Так может ли этот логический поток быть возможным примером? 1) Класс службы вызывает репозитории для извлечения сущности из БД, 2) Класс службы вызывает некоторые фабрики для создания экземпляра объекта домена, содержащего извлеченную сущность, 3) Класс службы вызывает метод объекта домена для выполнения бизнес-логики. 05.10.2017
  • №1 и №3 звучат нормально. # 2 трудно сказать, возможно, правильно, если ваша служба просто делегирует фабрики. Как насчет того, чтобы вы задали еще один вопрос SOF с примерами для обсуждения? 05.10.2017
  • Действительно обсуждение будет очень долгим. Еще раз большое спасибо за то, что нашли время ответить на мои вопросы один за другим. 06.10.2017
  • Новые материалы

    Угловая структура архитектуры
    Обратите внимание, что эта статья устарела, я решил создать новую с лучшей структурой и с учетом автономных компонентов: https://medium.com/@marekpanti/angular-standalone-architecture-b645edd0d54a..

    «Данные, которые большинство людей используют для обучения своих моделей искусственного интеллекта, поставляются со встроенным…
    Первоначально опубликовано HalkTalks: https://hacktown.com.br/blog/blog/os-dados-que-a-maioria-das-pessoas-usa-para-treinar-seus-modelos-de-inteligencia-artificial- ja-vem-com-um-vies-embutido/..

    Сильный ИИ против слабого ИИ: различия парадигм искусственного интеллекта
    В последние годы изучению и развитию искусственного интеллекта (ИИ) уделяется большое внимание и прогресс. Сильный ИИ и Слабый ИИ — две основные парадигмы в области искусственного интеллекта...

    Правильный способ добавить Firebase в ваш проект React с помощью React Hooks
    React + Firebase - это мощная комбинация для быстрого и безопасного создания приложений, от проверки концепции до массового производства. Раньше (знаете, несколько месяцев назад) добавление..

    Создайте API с помощью Python FastAPI
    Создание API с помощью Python становится очень простым при использовании пакета FastAPI. После установки и импорта вы можете создать приложение FastAPI и указать несколько конечных точек. Каждой..

    Веселье с прокси-сервером JavaScript
    Прокси-серверы JavaScript — это чистый сахар, если вы хотите создать некоторую общую логику в своих приложениях, чтобы облегчить себе жизнь. Вот один пример: Связь клиент-сервер Мы..

    Получить бесплатный хостинг для разработчиков | Разместите свой сайт за несколько шагов 🔥
    Статические веб-сайты — это веб-страницы с фиксированным содержанием и его постоянным содержанием. Но теперь статические сайты также обрабатывают динамические данные с помощью API и запросов...