none
Patron Services Generic RRS feed

  • Pregunta

  • Hola a todos,

    Tengo mi aplicacion web api en core 2.1 con ptrpn de repositorio y unitofwork y funciona correctamente, pero en mi capa de servicios el codigo se repite sobre todo para el crud, como puedo generar mi servicio generico utilizando mi unitofwork y mi repositorio generico y mapper. adjunto el codigo que utilizo en mi servicio.

    public class ApplicationService : IApplicationService
        {
            private readonly IUnitOfWork _uow;
            private readonly IMapper _mapper;
    
            public ApplicationService(IUnitOfWork uow, IMapper mapper)
            {
                _uow = uow;
                _mapper = mapper;
            }
    
            /// <summary>
            /// Obiene una Lista
            /// </summary>
            /// <returns></returns>
            public async Task<List<ApplicationDto>> GetListAsync()
            {
              
                var result = await _uow.AuthApplication.GetAllAsyn();
                return _mapper.Map<List<ApplicationDto>>(result);
              
            }

    muchas gracias por la ayuda.


    Luis Ormeño

    sábado, 7 de julio de 2018 21:10

Respuestas

  • hola

    >>en la clase BaseService quise implemetar el codigo generico pero no reconoce TEntity y no encuentro la manera de que acepte el generico como entidad

    es que el UoW tambien debes hacerlo generico, no puedes usar: _uow.Tentity.GetAllAsyn();

    deberia ser ago como: _uow.GetAllAsyn<Tentity>();

    o quizas la clase de UoW tenga este generico, y no exponer una propiedad por cada entidad

    buscaste implementaciones genericas de UoW ?

    >>veo tu ejemplo e indicas poner el codigo en ApplicaconnService, pero el mismo codigo estaria en todas las clases de servicio donde tenga que obtener toda la tabla

    es que vas a necesitar la clase especializada para la entidad ya que seguramente tengas algun caso en donde necesites quizas obtener las application por fecha, o por algun item en concreto, esto no vas a poder hacerlo generico

    saludos


    Leandro Tuttini

    Blog
    MVP Profile
    Buenos Aires
    Argentina

    • Marcado como respuesta Luis Ormeño A lunes, 9 de julio de 2018 17:51
    lunes, 9 de julio de 2018 15:04

Todas las respuestas

  • hola

    no evaluaste crear una clase base de la cual hereden la funcionalidad comun, algo como ser

    interface IBaseService<T> 
    {
    	async Task<List<T>> GetListAsync();
    }
    
    public class BaseService<T> : IBaseService<T>   
    {
    
    	private readonly IUnitOfWork _uow;
    	private readonly IMapper _mapper;
    
    	public BaseService(IUnitOfWork uow, IMapper mapper)
    	{
    		_uow = uow;
    		_mapper = mapper;
    	}
    
    	public async Task<List<T>> GetListAsync()
    	{
    		
    	}
    
    
    }
    
    public class ApplicationService : BaseService<ApplicationDto>, IApplicationService
    {
    	public ApplicationService(IUnitOfWork uow, IMapper mapper) 
    		: base(uow, mapper)
    	{
    
    	}
    
    	//codigo especifico para application
    	
    
    }
    saludos

    Leandro Tuttini

    Blog
    MVP Profile
    Buenos Aires
    Argentina

    domingo, 8 de julio de 2018 18:57
  • Hola Leandro 

    Gracias por la respuesta, trate de hacerlo como le indicas pero ahi es donde me encontre el problema; en la clase BaseService quise implemetar el codigo generico pero no reconoce TEntity y no encuentro la manera de que acepte el generico como entidad.

    var result = await _uow.Tentity.GetAllAsyn();

    para no repetir el mismo codigo en todas las clases de servicio; veo tu ejemplo e indicas poner el codigo en ApplicaconnService, pero el mismo codigo estaria en todas las clases de servicio donde tenga que obtener toda la tabla y eso lo veo mal,por ello busco factorizar el codigo. Solo colocar en ApplicationService codigo unico de ese servicio.

    adjunto mi IUnitofWork

     public interface IUnitOfWork : IDisposable
        {
            int Complete();
            Task<int> CompleteAsync();
    
            IClientRepository AuthClient { get; }
            IRolRepository AuthRol { get; }
            IUserRepository AuthUser { get; }
            IUserRolRepository AuthUserRol { get; }
            ITokenRepository AuthRefreshToken { get; }
            IApplicationRepository AuthApplication { get; }
            IModuleRepository AuthModule { get; }
            IMenuRepository AuthMenu { get; }
            IOptionRepository AuthOption { get; }
            IViewRepository AuthView { get; }
            IPasswordRepository AuthPassword { get; }
    
    
        }

    adjunto mi UnitofWork

    public class UnitOfWork : IUnitOfWork
        {
            private AuthContext _context;
            string _errorMessage = string.Empty;
    
            public UnitOfWork(AuthContext context)
            {
                _context = context;
    
                AuthClient = new ClientRepository(_context);
                AuthRol = new RolRepository(_context);
                AuthUser = new UserRepository(_context);
                AuthUserRol = new UserRolRepository(_context);
                AuthRefreshToken = new TokenRepository(_context);
                AuthApplication = new ApplicationRepository(_context);
                AuthModule = new ModuleRepository(_context);
                AuthMenu = new MenuRepository(_context);
                AuthOption = new OptionRepository(_context);
                AuthView = new ViewRepository(_context);
                AuthPassword = new PasswordRepository(_context);
    
            }
    
            public IClientRepository AuthClient { get; }
            public IRolRepository AuthRol { get; }
            public IUserRepository AuthUser { get; }
            public IUserRolRepository AuthUserRol { get; }
            public ITokenRepository AuthRefreshToken { get; }
            public IApplicationRepository AuthApplication { get; }
            public IModuleRepository AuthModule { get; }
            public IMenuRepository AuthMenu { get; }
            public IOptionRepository AuthOption { get; }
            public IViewRepository AuthView { get; }
            public IPasswordRepository AuthPassword { get; }
    
            public int Complete()
            {
                try
                {
                    return _context.SaveChanges();
                   
                }
                catch (Exception ex)
                {
                    RollBack();
                    throw new Exception(_errorMessage, ex);
                }
               
            }
    
            public Task<int> CompleteAsync()
            {
                try
                {
                    return _context.SaveChangesAsync();
                }
                catch (Exception ex)
                {
                    RollBack();
                    throw new Exception(_errorMessage, ex);
                }
                
            }
    
            public void Dispose()
            {
                Dispose(true);
                GC.SuppressFinalize(this);
            }
            private void Dispose(bool disposing)
            {
                if (!disposing) return;
                if (_context == null) return;
                _context.Dispose();
                _context = null;
           
            }
    
            public void RollBack()
            {
                _context.ChangeTracker.Entries().ToList().ForEach(x => x.Reload());
            }
    
        }

    Te agradeceria la ayuda de este problema


     


    Luis Ormeño



    • Editado Luis Ormeño A domingo, 8 de julio de 2018 20:44 agregar codigo
    domingo, 8 de julio de 2018 20:39
  • hola

    >>en la clase BaseService quise implemetar el codigo generico pero no reconoce TEntity y no encuentro la manera de que acepte el generico como entidad

    es que el UoW tambien debes hacerlo generico, no puedes usar: _uow.Tentity.GetAllAsyn();

    deberia ser ago como: _uow.GetAllAsyn<Tentity>();

    o quizas la clase de UoW tenga este generico, y no exponer una propiedad por cada entidad

    buscaste implementaciones genericas de UoW ?

    >>veo tu ejemplo e indicas poner el codigo en ApplicaconnService, pero el mismo codigo estaria en todas las clases de servicio donde tenga que obtener toda la tabla

    es que vas a necesitar la clase especializada para la entidad ya que seguramente tengas algun caso en donde necesites quizas obtener las application por fecha, o por algun item en concreto, esto no vas a poder hacerlo generico

    saludos


    Leandro Tuttini

    Blog
    MVP Profile
    Buenos Aires
    Argentina

    • Marcado como respuesta Luis Ormeño A lunes, 9 de julio de 2018 17:51
    lunes, 9 de julio de 2018 15:04
  • Hola Leandro

    Seguí tu consejo y cambie mi interfaces y clase del UnitOfWork a Generic y funciono mis Servicios como lo esperaba y ya no tengo codigo repetido en mis servicios. Gracias por la orientación.


    Luis Ormeño

    lunes, 9 de julio de 2018 17:51