Как совместить два сервиса в один - PullRequest
0 голосов
/ 29 марта 2019

У меня есть два класса, как следующие

@Service
class BookService {
    @Autowired 
    BookRepository repository;

    public Book findById(Long id){
        Book book =  repository.findById(id);
        if (book==null){
            throw new EntityNotFoundException("Entity Not found with given id: "+id);
        }
        return book;
    }

    public Book save(Book book){
        return repository.save(book);
    }
}



@Service
class AuthorService {
    @Autowired
    AuthorRepository repository;

    public Author findById(Long id){
        Author author =  repository.findById(id);
        if (author==null){
            throw new EntityNotFoundException("Entity Not found with given id: "+id);
        }
        return author;
    }

    public Author save(Author author){
        return repository.save(author);
    }
}

Если вы посмотрите внимательно, то увидите, что оба выглядят почти одинаково. Разница лишь в том, что они оба имеют дело с двумя отдельными объектами.

Так есть ли вообще написать один класс для работы с такого рода дубликатами?

Ответы [ 2 ]

2 голосов
/ 29 марта 2019

Используйте логику объектного программирования:

   @Service
    class RepService {
        IRepository = repositoryClass;

        public T FindById<T>(Long id) where T : class {
            T findItem =  repository.findById(id);
            if (author==null){
                throw new EntityNotFoundException("Entity Not found with given id: "+id);
            }
            return findItem;
        }

        public T Save<T>(T obj) where T : class {
             return repository.Save(obj);
        }
    }

Затем вам понадобятся BookRepository и AuthorRepository для реализации IRepository.Также им нужно инициировать свой соответствующий repositoryClass в конструкторе.

1 голос
/ 30 марта 2019

Вы можете создать общие CrudService<T, ID> и CrudAbstractService<T, ID> с логикой по умолчанию для хранения / извлечения ваших объектов, например.

public interface CrudService<T, ID> {
    T save(T entity);

    T find(ID id);
}

public abstract class CrudAbstractService<T, ID> implements CrudService<T, ID> {

    private final JpaRepository<T, ID> repository;

    public CrudAbstractService(JpaRepository<T, ID> repository) {
        this.repository = repository;
    }

    @Override
    public T save(T entity) {
        return repository.save(entity);
    }

    @Override
    public T find(ID id) {
        return repository.findById(id)
                .orElseThrow(() -> new EntityNotFoundException("Entity Not found with given id: " + id));
    }

}

А затем просто расширьте свой BookService или любой другой сервис с помощью этой логики

public interface BookService extends CrudService<Book, Long> {
    // service-specific methods for example findBooksByAuthor(String author);
}
@Service
public class BookServiceImpl extends CrudAbstractService<Book, Long> implements BookService {

    private final BookRepository repository;

    @Autowired
    public BookServiceImpl(BookRepository repository) {
        super(repository);
        this.repository = repository;
    }

    // implement here service-specific logic from BookService interface

}

Тогда вы могли бы создать CrudController для этих операций и использовать его в своих сущностях.

public abstract class CrudController<T, ID> implements CrudService<T, ID> {

    private final CrudService<T, ID> service;

    public CrudController(CrudService<T, ID> service) {
        this.service = service;
    }

    @PostMapping
    public T save(@RequestBody T entity) {
        return service.save(entity);
    }

    @GetMapping("/{id}")
    public T find(@PathVariable ID id) {
        return service.find(id);
    }
}
@RestController
@RequestMapping("/books")
public class BookController extends CrudController<Book, Long> {

    private final BookService service;

    @Autowired
    public BookController(BookService service) {
        super(service);
        this.service = service;
    }
    // other BookService specific logic
}

Обратите внимание, что этот подход может увеличить сложность вашего кода, но он уменьшает дублирование и создает многоразовый механизм для операций CRUD. Вы должны выбрать между этими параметрами. Если ваше приложение маленькое и не расширяемое , лучше использовать простое дублирование .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...