I am new to ASP.NET MVC, and I'm creating an app for attending music events. There is a button for user to follow an artist to get all upcoming events.
When clicking on that button I get an error:
Entities in 'ApplicationDbContext.Followings' participate in the 'ApplicationUser_Followees' relationship. 0 related 'ApplicationUser_Followees_Source' were found. 1
This is the code of the model:
public class Following
{
public ApplicationUser Followers { get; set; }
public ApplicationUser Followees { get; set; }
[Key]
[Column(Order = 1)]
public string FollowerId { get; set; }
[Key]
[Column(Order = 2)]
public string FolloweeId { get; set; }
}
and this is code of the fluent api to build the data :
public class ApplicationDbContext : IdentityDbContext<ApplicationUser>
{
public DbSet<Following> Followings { get; set; }
public ApplicationDbContext()
: base("DefaultConnection", throwIfV1Schema: false)
{
}
public static ApplicationDbContext Create()
{
return new ApplicationDbContext();
}
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<ApplicationUser>()
.HasMany(u => u.Followers)
.WithRequired(f => f.Followees)
.WillCascadeOnDelete(false);
modelBuilder.Entity<ApplicationUser>()
.HasMany(u => u.Followees)
.WithRequired(f => f.Followers)
.WillCascadeOnDelete(false);
base.OnModelCreating(modelBuilder);
}
}
This is the controller for the following api :
public class FollowingsController : ApiController
{
private readonly ApplicationDbContext _context;
public FollowingsController()
{
_context = new ApplicationDbContext();
}
[HttpPost]
public IHttpActionResult Follow(FollowingDto dto)
{
var userId = User.Identity.GetUserId<string>();
Console.WriteLine(userId);
var exists = _context.Followings.Any(f => f.FollowerId == userId && f.FolloweeId == dto.FolloweeId);
if (exists)
return BadRequest("The following already exists");
var following = new Following
{
FollowerId = userId,
FolloweeId = dto.FolloweeId
};
_context.Followings.Add(following);
_context.SaveChanges();
return Ok();
}
}
This is the dto object :
public class FollowingDto
{
public string FolloweeId { get; set; }
}
This is the frontend code for the homepage where the following button is located:
@model Gighub.ViewModels.GigsViewModel
@{
ViewBag.Title = "Home Page";
}
<ul class="gigs">
@foreach (var gig in Model.UpComingGigs)
{
<li>
<div class="details">
<span class="artist">
@gig.Artist.Name @if (Model.ShowActions) {
<button class="btn btn-link btn-sm js-toggle-following" data-user-id="@gig.ArtistId">Follow?</button>
}
</span>
</div>
</li>
}
</ul>
@section scripts {
<script>
$(document).ready(function () {
$(".js-toggle-following").click(function (e) {
var btn = $(e.target);
$.post("/api/followings", { "FolloweeId": btn.attr("data-user-id") })
.done(function () {
btn.text("following")
})
.fail(function () {
alert("something failed");
});
});
});
</script>
}
and here is applicationuser class :
public class ApplicationUser : IdentityUser
{
public ICollection<Following> Followers { get; set; }
public ICollection<Following> Followees { get; set; }
public ApplicationUser()
{
Followers = new Collection<Following>();
Followees = new Collection<Following>();
}
[Required]
[StringLength(100)]
public string Name { get; set; }
public async Task<ClaimsIdentity> GenerateUserIdentityAsync(UserManager<ApplicationUser> manager)
{
// Note the authenticationType must match the one defined in CookieAuthenticationOptions.AuthenticationType
var userIdentity = await manager.CreateIdentityAsync(this, DefaultAuthenticationTypes.ApplicationCookie);
// Add custom user claims here
return userIdentity;
}
}