ICollection of Users in a relationship One to many

asp.net-core asp.net-identity entity-framework-core postman

Question

I'have a application that has a relationship One to many with AspnetUser and when I do a GET request on Postman I don't receive all the user information, only a broken JSON with only the custom user data.

I've try to debug the code and I noticed before I send the information all data is inside the object that I send.

ControllerBase:

    [HttpGet]
    public async Task<IActionResult> GetClasses ()
    {
        var classes = await_repository.All.ToListAsync();
        return Ok(classes);

    }

Repository:

public IQueryable<TEntity> All => _context.Set<TEntity>().AsQueryable();

Classes Model

    public partial class Classes
    {

      public Classes()
      {
        Users = new HashSet<UserApplication>();
      }

      public int Id { get; set; }
      public string Name { get; set; }

      public virtual ICollection<UserApplication> Users { get; set; }
    }

UserApplication

public class UserApplication : IdentityUser
{

    public string Name { get; set; }

    public int Age { get; set; }
    public int ClassesId { get; set; }
    public virtual Classes Classes { get; set; }
}

Entity Configuration

            builder.HasOne(d => d.Classes)
            .WithMany(p => p.Users)
            .HasForeignKey(d => d.ClassesId)
            .OnDelete(DeleteBehavior.ClientSetNull)
            .HasConstraintName("Users_ClassesId_fkey");

So, when I debugged on Visual Studio the var classes has all attributes full, but when I use the Postman I got this result

Result of the GET on Postman

[{"id":1,"name":"Test","users":[{"name":"Teste123","age":18, "classesId":1

I read some articles saying that you have to make to table users to resolve this, but I felt like too "trick" to do this.

1
0
3/1/2019 9:00:00 PM

Accepted Answer

The problem of self-referencing loops during JSON serialization is connected to how EFCore loads related data (docs). When you load a collection, related entities may or may not be automatically populated depending on whether or not those object have been previously loaded. It's called automatic fix-up of navigation properties. Alternatively, they may be eagerly loaded via .Include().

Whenever you get a self-referencing graph of entities to be serialized, there are several options:

  • Newtonsoft.Json.ReferenceLoopHandling.Ignore (officially recommended). It works but still can result in serializing excessive data if self-reference occurs deep in the hierarchy.

  • [JsonIgnore] attribute on navigation properties. As you noted, attributes disappear when model classes are regenerated. Thus, their use can be inconvenient.

  • (Best choice) Pre-select a subset of properties:

    var minimallyNecessarySet= _nwind.Products.Select(p => new {
        p.ProductID,
        p.ProductName,
        p.UnitPrice,
        p.CategoryID
    });
    
    return minimallyNecessarySet.ToList();
    

    This approach has the advantage of serializing only required data. It's compatible with DevExtreme's DataSourceLoader:

    return DataSourceLoader.Load(minimallyNecessarySet, loadOptions);
    
3
2/27/2018 10:28:08 AM


Related Questions





Related

Licensed under: CC-BY-SA with attribution
Not affiliated with Stack Overflow
Licensed under: CC-BY-SA with attribution
Not affiliated with Stack Overflow