简体   繁体   中英

Using data from a table and foreign key table in single query

hard to explain from title, hopefully this description helps explain the situation. I have a music app where a user can create a playlist. So I set up two tables.

One called Playlists (columns: PlaylistID, PlaylistName, CreatorID) and another called PlaylistSongs (columns: PlaylistSongID, PlaylistID, and SongID). I have a foreign key connection between the PlaylistID columns.

I want to display a list of playlists on the home page, each one looks like this: 在此处输入图片说明

I can pull the playlist name from Playlist table and display properly....easy. The issue I am having is figuring out how to display the metadata such as the artists (Sasha Sloan ODESZA etc) which I can obtain from the SongID from the PlaylistSongs table which is connected by foreign key.

Here's what I have right now:

Controller

public ActionResult Playlists()
{
    var model = new HomePlaylistViewModel();
    model.Playlists = EntityDataAccess.GetFeaturedPlaylistsByCount(6);

    return View(model);
}

Model:

public class HomePlaylistViewModel
{
    public List<Playlist> Playlists { get; set; }
    public List<PlaylistSong> PlaylistSongs { get; set; }
    public List<Album> Albums { get; set; }
}

CSHTML:

<div class="playlists-container">

            @foreach (var item in Model.Playlists)
            {
                <div class="playlist-album">
                    <div class="album-grad"></div>
                    <a href="#">
                        <h1>
                            @item.PlaylistName
                        </h1>

                        <div class="playlist-desc-container">
                                <h4 class="playlist-desc">Featuring: INSERT ARTIST NAMES HERE</h4>
                                <h4 class="playlist-creator"> Songs &#8226; Curated by
                           </h4>
                        </div>

                        <img src="https://ucarecdn.com/6d669906-60df-4f26-bf80-f11eef3bd019/-/format/jpeg/-/quality/lightest/" class="playlist-album-art">
                    </a>
                    <button class="ui button playlist-listen">LISTEN</button>
                    <button class="ui button playlist-collect"><i class="material-icons">playlist_add</i></button>
                </div>
            }

Playlist.cs

public partial class Playlist
{
    [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2214:DoNotCallOverridableMethodsInConstructors")]
    public Playlist()
    {
        this.PlaylistSongs = new HashSet<PlaylistSong>();
    }

    public int PlaylistID { get; set; }
    public string PlaylistName { get; set; }
    public int CreatorID { get; set; }

    [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2227:CollectionPropertiesShouldBeReadOnly")]
    public virtual ICollection<PlaylistSong> PlaylistSongs { get; set; }
}

EntityDataAccess.cs

public static List<Playlist> GetFeaturedPlaylistsByCount(int count)
        {
            using (var Context = GetContext())
            {
                return Context.Playlists.Take(count).ToList();
            }
        }

So I essentially have a model with this Playlist info:

  • PlaylistID
  • PlaylistName
  • CreatorID

I need to use each unique PlaylistID to access the songs in the PlaylistSongs table that have that PlaylistID so I can display on screen. Does that make sense?

EDIT: Added call to context and corresponding class

public static UnearthEntities GetContext()
        {
            var context = new UnearthEntities();
            context.Configuration.ProxyCreationEnabled = false;
            return context;
        }

Unearth Entities:

public partial class UnearthEntities : DbContext
    {
        public UnearthEntities()
            : base("name=UnearthEntities")
        {
        }

        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {
            throw new UnintentionalCodeFirstException();
        }

        public virtual DbSet<AccountInfo> AccountInfoes { get; set; }
        public virtual DbSet<Album> Albums { get; set; }
        public virtual DbSet<AlbumTag> AlbumTags { get; set; }
        public virtual DbSet<AspNetRole> AspNetRoles { get; set; }
        public virtual DbSet<AspNetUserClaim> AspNetUserClaims { get; set; }
        public virtual DbSet<AspNetUserLogin> AspNetUserLogins { get; set; }
        public virtual DbSet<AspNetUser> AspNetUsers { get; set; }
        public virtual DbSet<DownloadHistory> DownloadHistories { get; set; }
        public virtual DbSet<Song> Songs { get; set; }
        public virtual DbSet<Spotlight> Spotlights { get; set; }
        public virtual DbSet<Video> Videos { get; set; }
        public virtual DbSet<FeaturedAlbum> FeaturedAlbums { get; set; }
        public virtual DbSet<Key> Keys { get; set; }
        public virtual DbSet<SongPlayDaily> SongPlayDailies { get; set; }
        public virtual DbSet<Favorite> Favorites { get; set; }
        public virtual DbSet<License> Licenses { get; set; }
        public virtual DbSet<Product> Products { get; set; }
        public virtual DbSet<Playlist> Playlists { get; set; }
        public virtual DbSet<PlaylistSong> PlaylistSongs { get; set; }
    }

Refer to Microsoft's article: Entity Framework Loading Related Entities

Assuming your data context is correct, use the Include to bring in the related data, like:

return Context.Playlists.Include("PlaylistSongs").Take(count).ToList();

BTW: For clarity, I would rename some of your fields. For example, primary key (PK) field names need not be prefixed with the name of the table. It gets confusing. Just name your PK field "Id". When referring to a key field from within a related table, then use the table name. For example, to make a one-to-many relationship between Playlists, and PlaylistSongs, a field named PlaylistId would exist in the table PlaylistSongs.

Regarding the building of a model, take a look at Microsoft's documents Creating a Model and Foreign Key Constraints . The first provides a link to github repo of sample code.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM