C# 将两个视图合并为一个视图,而不是为同一控制器操作返回两个视图

C# 将两个视图合并为一个视图,而不是为同一控制器操作返回两个视图,c#,asp.net-mvc,razor,C#,Asp.net Mvc,Razor,在ASP.NET MVC中,我有一个BooksController,它提供了查看书籍的功能。我希望www.mydomain.com/books返回我所有书籍的列表(以及与之关联的“所有书籍”html页面),而www.domain.com/books/c-sharp-for-dummies获取“c#for dummies”书籍的所有信息(同样是“单本书”html页面) 使用bookName参数创建Index方法非常简单 public class BooksController { pub

在ASP.NET MVC中,我有一个
BooksController
,它提供了查看书籍的功能。我希望
www.mydomain.com/books
返回我所有书籍的列表(以及与之关联的“所有书籍”html页面),而
www.domain.com/books/c-sharp-for-dummies
获取“c#for dummies”书籍的所有信息(同样是“单本书”html页面)

使用
bookName
参数创建
Index
方法非常简单

public class BooksController
{
     public ActionResult Index(string bookName)
     {
         if (string.IsNullOrEmpty(bookName)
         {
           //return all books here
         }
         else
         {
            //return single book here 
         }
     }
}
Index
有一个关联的
Index.cshtml
查看页面,但是我必须在视图中做一个剃刀检查,以确定是加载“所有书籍”HTML/CSS,还是加载“单一书籍”HTML/CSS-这就像视图包含一个页面中的两个页面,我觉得这违反直觉

对于这种情况,什么是好的(甚至是传统的)方法?我是否只创建两个
cshtml
文件,一个用于“所有书籍”,另一个用于“单个书籍”,然后根据是否提供了
bookName
参数返回相应的视图

public class BooksController
{
     public ActionResult Index(string bookName)
     {
         if (string.IsNullOrEmpty(bookName)
         {
           //return all books viewmodel and related  view             
         }
         else
         {
            //return single book viewmodel and related view 
         }
     }
}

您应该在控制器中创建两个单独的操作方法。一个用于返回包含所有书籍的视图,另一个用于返回单个书籍的详细信息

您可以用这种方式定义路由定义,以便请求来自
yourSite/books
,它将由index操作处理,而
yourSite/books/somebookname
,它将由
Details
操作方法处理。以下是您将如何使用


现在,在
index.cshtml
视图中,您可以显示所有书籍,在
Details.cshtml
视图中,您可以显示特定书籍的详细信息。

您应该在控制器中创建两个单独的操作方法。一个用于返回包含所有书籍的视图,另一个用于返回单个书籍的详细信息

您可以用这种方式定义路由定义,以便请求来自
yourSite/books
,它将由index操作处理,而
yourSite/books/somebookname
,它将由
Details
操作方法处理。以下是您将如何使用


现在,在
index.cshtml
视图中,可以显示所有书籍,在
Details.cshtml
视图中,可以显示特定书籍的详细信息。

index
方法通常用于显示与控制器关联的项目集合,以及单独的
详细信息(字符串bookName)
方法用于显示单个项目的详细信息我将默认使用所有图书数据的视图,并在选择图书时异步加载部分视图以覆盖该数据两个视图(可选两个操作)将是一种比单一视图更常见的方法。@Stephenmueecke谢谢-如果我们假设我不想将
/details/
作为我的URL的一部分(假设所有书籍都是
/books
,一本书是
/books/{bookId}/{bookName}
),你会如何处理?我想不出比@Shyju在其答案中提出的解决方案更好的解决方案。Shyju的答案确实说明了如何做到这一点(使用属性路由,尽管您也可以在
RouteConfig
文件中定义路由)。如果您想在路由中也使用ID,您只需使用
[Route(“books/{bookId}/{bookName}”)]
(但这表明您可能需要根据的slug路由,
Index
方法通常用于显示与控制器关联的项目集合,以及单独的
详细信息(string bookName)
方法用于显示单个项目的详细信息我将默认使用所有图书数据的视图,并在选择图书时异步加载部分视图以覆盖该数据两个视图(可选两个操作)这将是一种比单一视图更常见的方法。@Stephenmueecke谢谢-如果我们假设我不想将
/details/
作为我的URL的一部分(假设所有书籍都是
/books
,而一本书是
/books/{bookId}/{bookName}
),你会怎么做?我想不出更好的方法了解决方案是@Shyju在其答案中提出的。Shyju的答案确实说明了如何做到这一点(使用属性路由,尽管您也可以在
RouteConfig
文件中定义路由)。如果您希望路由中也包含ID,您只需使用
[Route(“books/{bookId}/{bookName}”)]
(但这表明您可能需要按照Thanke@Shyju进行slug路由,这是否意味着我必须在每个方法的顶部定义
Route
?使用
RouteConfig
可以实现类似的效果吗?是的。您也可以使用常规路由实现相同的效果(检查相同的链接)但是,我想,属性路由更容易理解谢谢@Shyju,这是否意味着我必须在每个方法的顶部定义
Route
?使用
RouteConfig
可以实现类似的效果吗?是的。使用传统路由也可以实现同样的效果(检查相同的链接).但依我看,属性路由更具可读性
public class BooksController : Controller
{
    [Route("books")]
    public ActionResult Index()
    {
        // to do : Get all the books and pass it to the view.
        return View();
    }
    [Route("books/{bookName}")]
    public ActionResult Details(string bookName)
    {
       // to do : Get single book using the bookName parameter
       // and pass that to the view.
       return View();
    }
}