System.nullreferenceexception en el patrón de repositorio

programación


en el sistema de patrones de repositorio.NullReferenceException
Eliminar método

System.NullReferenceException
HResultado=0x80004003
Mensaje=Referencia de objeto no establecida como instancia de un objeto.
Fuente=Microsoft.EntityFrameworkCore
Seguimiento de pila:
en Microsoft.EntityFrameworkCore.Internal.EntityFinder`1.ValidateKeyPropertiesAndExtractCancellationToken(Objeto[] keyValues, booleano asíncrono, CancellationToken (cancelaciónToken)
en Microsoft.EntityFrameworkCore.Internal.EntityFinder`1.Find(Objeto[] valores clave)
en BL.Repositories.BaseRepository`1.GetById(Nullable`1 id) en E:\Programming\Folder\SoqRepository\BL\Repositories\BaseRepository.cs:línea 51

Lo que he probado:

Clase de base de datos

C#
using System;
using System.Collections.Generic;

namespace Sq.Models;

public partial class VwItem
{
    public string ItemName { get; set; } = null!;
    public decimal PurchasePrice { get; set; }
    public decimal SalesPrice { get; set; }
    public int CategoryId { get; set; }
    public string? ImageName { get; set; }
    public DateTime CreatedDate { get; set; }
    public string CreatedBy { get; set; } = null!;
    public int CurrentState { get; set; }
    public string? UpdatedBy { get; set; }
    public DateTime? UpdatedDate { get; set; }
    public string? Description { get; set; }
    public string? Gpu { get; set; }
    public string? HardDisk { get; set; }
    public int? ItemTypeId { get; set; }
    public string? Processor { get; set; }
    public int? RamSize { get; set; }
    public string? ScreenReslution { get; set; }
    public string? ScreenSize { get; set; }
    public string? Weight { get; set; }
    public int? OsId { get; set; }
    public string CategoryName { get; set; } = null!;
    public string ItemTypeName { get; set; } = null!;
    public string OsName { get; set; } = null!;
    public int ItemId { get; set; }
}

Interfaz de clase

C#
using Sq.Models;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Domain.Interfaces
{
    public interface IBaseRepository <t> where T : class
    {
        public IEnumerable<t>GetAll();
        public IEnumerable<t> GetAll(Func<t, bool=""> Condition);
        public T GetById(int? id);
        public void Delete(T Entity);
        public void ChangeState(int id);
    }
}

C#
using Domain.Interfaces;
using Sq.BL;
using Sq.Models;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace BL.Repositories
{
    public class BaseRepository<t> : IBaseRepository<t> where T : class
    {
        public LapShopContext LapShopContext;
        public BaseRepository(LapShopContext _LapShopContext)
        {
            LapShopContext = _LapShopContext ?? throw new ArgumentNullException(nameof(_LapShopContext));
        }

implementar interfaz

C#
using Sq.Models;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Domain.Interfaces
{
    public interface IBaseRepository <t> where T : class
    {
        public T GetById(int? id);
        public void Delete(T Entity);
    }
}
        public T GetById(int? id)
        {
            try
            {
                return LapShopContext.Set<t>().Find(id);
            }
            catch (Exception)
            {
                return null;
            }
        }

        public void Delete(T entity)
        {
            try
            {
                LapShopContext.Set<t>().Remove(entity);
                LapShopContext.SaveChanges();
            }
            catch (Exception)
            {
             return;
            }
        }

Controlador

C#
public ActionResult Delete(int ItemId)
{
    if (ItemId == null)
    {

        return BadRequest("ItemId is null");
    }

    var Obj = baseRepository.GetById(ItemId);
    baseRepository.Delete(Obj);

    return RedirectToAction("List");
}

Solución 1

Como muestra el mensaje de error, el problema está en el método Eliminar. El método Eliminar intenta eliminar una entidad del contexto usando LapShopContext.Set().Remove(entidad). Sin embargo, el error que está encontrando es una excepción NullReferenceException, que sugiere que el parámetro de entidad es nulo. El problema puede deberse a que el método GetById devuelve un valor nulo cuando no se encuentra la identificación especificada y no está verificando el valor nulo antes de llamar a Eliminar. Puede modificar el código del controlador como se muestra a continuación:

C#
public ActionResult Delete(int ItemId)
{
    if (ItemId == 0)
    {
        return BadRequest("ItemId is invalid");
    }
    var Obj = baseRepository.GetById(ItemId);
    if (Obj == null)
    {
        return NotFound($"Item with ID {ItemId} not found");
    }
    baseRepository.Delete(Obj);
    return RedirectToAction("List");
}

Solución 2

Dado que el código de su repositorio se traga todas las excepciones, ¡por cierto, es una idea extremadamente mala! – la única razón para un NullReferenceException sería que el baseRepository es null.

Verifique el constructor para asegurarse de haber asignado el campo correctamente y genere una excepción si el valor que asignó resulta ser null:

C#
public YourControler(IBaseRepository<YourItem> baseRepository)
{
    this.baseRepository = baseRepository ?? throw new ArgumentNullException(nameof(baseRepository));
}

También:

C#
public ActionResult Delete(int ItemId)
{
    if (ItemId == null)

Un int nunca puede ser null. El compilador generará un CS0472 advertencia en esa línea.

コメント

タイトルとURLをコピーしました