Miranda's Musings

computer articles, politics, and more

Showing multiple models on one page

There are times when you will need to show multiple models on a single MVC view. In this post I will show how to accomplish that.   

I will be using my Library solution for this tutorial.  In this case I will be using the Models related to Movies. 

Those models are Movie, Actor, Genre, and Format.  These are all tables in the database as well.  However, there are also some foreign key tables to handle the one to many relationships that are possible with Movie to Actor, Movie to Genre, Movie to Format and.  

The view will be displaying information on the selected movie from my database, including the different actors, the formats I have the movie in, and the different genres the movie fits in. 

example

Title
A Million Ways To Die In The West
Rating
NR
Stars
4.00
Actors
Seth  MacFarlane
Neil Patrick  Harris
Liam  Neeson
Sarah  Silverman
Charlize  Theron
Formats
Digital
Genres
Comedy
Western

 

The tables are set up as such 

USE [Library]
GO
/****** Object:  Table [dbo].[ActorMovies]    Script Date: 11/21/2023 3:51:21 PM ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[ActorMovies](
	[MovieID] [int] NOT NULL,
	[ActorID] [int] NOT NULL
) ON [PRIMARY]
GO
/****** Object:  Table [dbo].[Actors]    Script Date: 11/21/2023 3:51:21 PM ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[Actors](
	[ActorID] [int] IDENTITY(1,1) NOT NULL,
	[FirstName] [nvarchar](30) NOT NULL,
	[LastName] [nvarchar](40) NOT NULL,
PRIMARY KEY CLUSTERED 
(
	[ActorID] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON, OPTIMIZE_FOR_SEQUENTIAL_KEY = OFF) ON [PRIMARY]
) ON [PRIMARY]
GO
/****** Object:  Table [dbo].[Formats]    Script Date: 11/21/2023 3:51:21 PM ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[Formats](
	[FormatID] [int] IDENTITY(1,1) NOT NULL,
	[Name] [nvarchar](50) NOT NULL,
	[Book] [bit] NOT NULL,
PRIMARY KEY CLUSTERED 
(
	[FormatID] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON, OPTIMIZE_FOR_SEQUENTIAL_KEY = OFF) ON [PRIMARY]
) ON [PRIMARY]
GO
/****** Object:  Table [dbo].[Genres]    Script Date: 11/21/2023 3:51:21 PM ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[Genres](
	[Genre] [int] IDENTITY(1,1) NOT NULL,
	[Name] [nvarchar](100) NOT NULL,
PRIMARY KEY CLUSTERED 
(
	[Genre] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON, OPTIMIZE_FOR_SEQUENTIAL_KEY = OFF) ON [PRIMARY]
) ON [PRIMARY]
GO
/****** Object:  Table [dbo].[MovieFormat]    Script Date: 11/21/2023 3:51:21 PM ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[MovieFormat](
	[MovieID] [int] NOT NULL,
	[FormatID] [int] NOT NULL
) ON [PRIMARY]
GO
/****** Object:  Table [dbo].[MovieGenres]    Script Date: 11/21/2023 3:51:21 PM ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[MovieGenres](
	[MovieID] [int] NOT NULL,
	[Genre] [int] NOT NULL
) ON [PRIMARY]
GO
/****** Object:  Table [dbo].[Movies]    Script Date: 11/21/2023 3:51:21 PM ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[Movies](
	[MovieID] [int] IDENTITY(1,1) NOT NULL,
	[Title] [nvarchar](400) NOT NULL,
	[Rating] [nvarchar](5) NULL,
	[Stars] [decimal](18, 0) NULL,
PRIMARY KEY CLUSTERED 
(
	[MovieID] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON, OPTIMIZE_FOR_SEQUENTIAL_KEY = OFF) ON [PRIMARY]
) ON [PRIMARY]
GO
ALTER TABLE [dbo].[ActorMovies]  WITH CHECK ADD  CONSTRAINT [FK_ActorMovie] FOREIGN KEY([MovieID])
REFERENCES [dbo].[Movies] ([MovieID])
GO
ALTER TABLE [dbo].[ActorMovies] CHECK CONSTRAINT [FK_ActorMovie]
GO
ALTER TABLE [dbo].[ActorMovies]  WITH CHECK ADD  CONSTRAINT [FK_MovieActor] FOREIGN KEY([ActorID])
REFERENCES [dbo].[Actors] ([ActorID])
GO
ALTER TABLE [dbo].[ActorMovies] CHECK CONSTRAINT [FK_MovieActor]
GO
ALTER TABLE [dbo].[MovieFormat]  WITH CHECK ADD  CONSTRAINT [FK_FormatMovie] FOREIGN KEY([FormatID])
REFERENCES [dbo].[Formats] ([FormatID])
GO
ALTER TABLE [dbo].[MovieFormat] CHECK CONSTRAINT [FK_FormatMovie]
GO
ALTER TABLE [dbo].[MovieFormat]  WITH CHECK ADD  CONSTRAINT [FK_MovieFormat] FOREIGN KEY([MovieID])
REFERENCES [dbo].[Movies] ([MovieID])
GO
ALTER TABLE [dbo].[MovieFormat] CHECK CONSTRAINT [FK_MovieFormat]
GO
ALTER TABLE [dbo].[MovieGenres]  WITH CHECK ADD  CONSTRAINT [FK_GenreMovie] FOREIGN KEY([MovieID])
REFERENCES [dbo].[Movies] ([MovieID])
GO
ALTER TABLE [dbo].[MovieGenres] CHECK CONSTRAINT [FK_GenreMovie]
GO
ALTER TABLE [dbo].[MovieGenres]  WITH CHECK ADD  CONSTRAINT [FK_MovieGenre] FOREIGN KEY([Genre])
REFERENCES [dbo].[Genres] ([Genre])
GO
ALTER TABLE [dbo].[MovieGenres] CHECK CONSTRAINT [FK_MovieGenre]
GO

and the Models are set up as such

public class Actor
{ 
    public int ActorId { get; set; }

    [Required, Display(Name ="First Name"), MaxLength(30)]
    public string FirstName { get; set; }

    [Required, Display(Name ="Last Name"), MaxLength(40)]
    public string LastName { get; set; }

    public string Name { get; set; }
}

public class Format
{
    public int FormatID { get; set; }

   	[Required, MaxLength(50)]
    public string Name { get; set; }

   	[Required]
    public bool Book { get; set; }
}

public class Genre
{
    [Display(Name ="Genre")]
    public int GenreId { get; set; }

    [Required, MaxLength(100)]
    public string Name { get; set; }
}

public class Movie
{
    public int MovieId { get; set; }
	
    [Required,MaxLength(400)]
    public string Title { get; set; }

    [MaxLength(5)]
    public string Rating { get; set; }

    public decimal? Stars { get; set; }

    public int FormatId { get; set; }

    [Display(Name ="Format")]
    public string FormatName { get; set; }
}

 

The first thing we have to do is add some code to the movie model.  We need to let the model know that Actor, Genre and Format are collections.   This will allow for us to list the information for these on our view.

so we add this to the Movie model

 

        public virtual ICollection<Actor> Actor { get; set; }
        public virtual ICollection<Genre> Genre { get; set; }
        public virtual ICollection<Format> Format { get; set; }

        public Movie()
        {
            Actor = new HashSet<Actor>();
            Genre = new HashSet<Genre>();
            Format = new HashSet<Format>();
        }

 Now the class has the collections for the information so all we need to do is add the method to fill in the list.   

        public Movie GetMovie(int MovieId)
        {
            List<Actor> actorList = null;
            List<Format> formatList = null;
            List<Genre> genreList = null;
            using (SqlConnection oConn = new SqlConnection(ConfigurationManager.ConnectionStrings["DefaultConnection"].ConnectionString))
            {
                using (SqlCommand oCmd = new SqlCommand())
                {
                    try
                    {
                        oCmd.CommandText = "GetMovie";
                        oCmd.CommandType = CommandType.StoredProcedure;
                        oCmd.Parameters.Add("@MovieId",SqlDbType.Int).Value = MovieId;
                        oCmd.Connection = oConn;
                        oConn.Open();
                        using (SqlDataReader reader = oCmd.ExecuteReader())
                        {

                            Movie movie = new Movie();
                            while (reader.Read())
                            {
                                movie.MovieId = MovieId;
                                movie.Title = reader[0].ToString();
                                movie.Rating = reader[1].ToString();
                                movie.Stars = (decimal)reader[2];
                            }   
                            using (SqlConnection conn = new SqlConnection(ConfigurationManager.ConnectionStrings["DefaultConnection"].ConnectionString))
                            {
                                using (SqlCommand cmd = new SqlCommand())
                                {
                                    try
                                    {
                                        cmd.CommandText = "ListFormatsByMovie";
                                        cmd.CommandType = CommandType.StoredProcedure;
                                        cmd.Parameters.Add("@MovieId", SqlDbType.Int).Value = MovieId;
                                        cmd.Connection = conn;
                                        conn.Open();
                                        using (SqlDataReader rdr = cmd.ExecuteReader())
                                        {
                                            formatList = new List<Format>();
                                            while (rdr.Read())
                                            {
                                                Format format = new Format
                                                {
                                                    Name = rdr[0].ToString()
                                                };
                                                formatList.Add(format);
                                            }
                                        }
                                    }
                                    catch (Exception ex)
                                    {
                                        Errors.ErrorOccured(ex, "MovieId = " + MovieId);
                                        return null;
                                    }
                                    finally
                                    {
                                        conn.Close();
                                        cmd.Dispose();
                                    }
                                }
                            }
                            using (SqlConnection conn = new SqlConnection(ConfigurationManager.ConnectionStrings["DefaultConnection"].ConnectionString))
                            {
                                using (SqlCommand cmd = new SqlCommand())
                                {
                                    try
                                    {
                                        cmd.CommandText = "ListActorsByMovie";
                                        cmd.CommandType = CommandType.StoredProcedure;
                                        cmd.Parameters.Add("@MovieId", SqlDbType.Int).Value = MovieId;
                                        cmd.Connection = conn;
                                        conn.Open();
                                        using (SqlDataReader rdr = cmd.ExecuteReader())
                                        {
                                            actorList = new List<Actor>();
                                            while (rdr.Read())
                                            {
                                                Actor actor = new Actor
                                                {
                                                    FirstName = rdr[0].ToString(),
                                                    LastName = rdr[1].ToString()
                                                };
                                                actorList.Add(actor);
                                            }
                                        }
                                    }
                                    catch (Exception ex)
                                    {
                                        Errors.ErrorOccured(ex, "MovieId = " + MovieId);
                                        return null;
                                    }
                                    finally
                                    {
                                        conn.Close();
                                        cmd.Dispose();
                                    }
                                }
                            }
                            using (SqlConnection conn = new SqlConnection(ConfigurationManager.ConnectionStrings["DefaultConnection"].ConnectionString))
                            {
                                using (SqlCommand cmd = new SqlCommand())
                                {
                                    try
                                    {
                                        cmd.CommandText = "ListGenresByMovie";
                                        cmd.CommandType = CommandType.StoredProcedure;
                                        cmd.Parameters.Add("@MovieId", SqlDbType.Int).Value = MovieId;
                                        cmd.Connection = conn;
                                        conn.Open();
                                        using (SqlDataReader rdr = cmd.ExecuteReader())
                                        {
                                            genreList = new List<Genre>();
                                            while (rdr.Read())
                                            {
                                                Genre genre = new Genre
                                                {
                                                    Name = rdr[0].ToString()
                                                };
                                                genreList.Add(genre);
                                            }
                                        }
                                    }
                                    catch (Exception ex)
                                    {
                                        Errors.ErrorOccured(ex, "MovieId = " + MovieId);
                                        return null;
                                    }
                                    finally
                                    {
                                        conn.Close();
                                        cmd.Dispose();
                                    }
                                }
                            }
                            movie.Format = formatList;
                            movie.Actor = actorList;
                            movie.Genre = genreList;
                            return movie;
                        }                  
                    }
                    catch (Exception ex)
                    {
                        Errors.ErrorOccured(ex);
                        return null;
                    }
                    finally
                    {
                        oConn.Close();
                        oCmd.Dispose();
                    }
                }
            }
        }

Then it is just call the method from the controller

        public ActionResult Details(int?id)
        {
            try
            {
                if(id == null)
                {
                    return RedirectToAction("Index");
                }
                Movie movie = new Movie();
                var model = movie.GetMovie((int)id);
                return View(model);
            }
            catch (Exception ex)
            {
                Errors.ErrorOccured(ex);
            }
            return RedirectToAction("InternalServerError", "Error");
        }

And display in the view

@model Library.Models.Movie

@{
    ViewBag.Title = "Details";
}

<h2>Details</h2>

<div>
    <h4>Movie</h4>
    <hr />
    <dl class="dl-horizontal">
        <dt>
            @Html.DisplayNameFor(model => model.Title)
        </dt>

        <dd>
            @Html.DisplayFor(model => model.Title)
        </dd>

        <dt>
            @Html.DisplayNameFor(model => model.Rating)
        </dt>

        <dd>
            @Html.DisplayFor(model => model.Rating)
        </dd>

        <dt>
            @Html.DisplayNameFor(model => model.Stars)
        </dt>

        <dd>
            @Html.DisplayFor(model => model.Stars)
        </dd>

        <dt>
            Actors
        </dt>

        <dd>
            @foreach (var actor in Model.Actor)
	    {
                @actor.FirstName <span> </span>@actor.LastName <br />
	    }
        </dd>

        <dt>
            Formats
        </dt>

        <dd>
            @foreach (var frmt in Model.Format)
	    {
                @frmt.Name <br />
	     }
        </dd>

        <dt>
            Genres
        </dt>

        <dd>
            @foreach (var genre in Model.Genre)
	    {
                @genre.Name <br />
	    }
        </dd>

    </dl>
</div>

 

 OK  now you can see how to display multiple models in a single view.   I hope this helps.

Loading