ASP.NET MVC 5:在控制器中持久化变量



我在视图的GET请求中实例化"plate"对象,然后在发布表单时访问它。plate对象是用表单中的数据填充的。我也可以用它来存储传递的坐标吗?或者,做我试图实现的目标的惯用方式是什么?

谢谢!

public class DrawingController : Controller
{
Plate plate;
[HttpGet]
public ActionResult Index()
{   
plate = new Plate()
{
Holes = new Holes()
}
return View(plate);
}
// called by ajax when user clicks on "Save" to save the input coordinates
[HttpPost]
public void PassCoordinates(string coordinates)
{
// why is plate null here?
plate.Holes.coordinates = coordinates;
}
[HttpPost]
public ActionResult Index(Plate plate)
{
// I want to access plate.Holes.coordinates that I set in 'PassCoordinates'
// how can I achieve this?
}
}

您看到的是预期的行为,因为Http是无状态的

每次调用操作方法时,都会创建控制器的一个新对象。因此,在您的情况下,当您进行ajax调用时,它将创建一个DrawingController的新对象,该对象将具有类型为Plate的属性,但不会初始化为Plate对象。(您在Index方法调用中执行的)

如果你想获得相同的板实例,在你的PassCoordinates操作方法中,你可以用不同的方式

  1. 让您的ajax调用发布Plate结构的js对象,并在Plate类型的操作方法中有一个参数。当提交请求时,模型绑定器将能够构建新对象并映射不同项目的值

  2. 将Plate对象存储在持久的meedium中并读取它。因此,在您的Index操作方法中,您将创建对象,初始化proprety值,并将其存储到db表/会话状态等。您可以在第二个操作方法中从这个位置再次读取它。使用静态变量是的另一个选项

如果选择选项#2并选择使用会话/静态变量,请记住,您正在尝试将有状态行为添加到无状态http:(

IMHO,选择1是一条路保持Http的无状态行为。让您的客户端代码(进行ajax调用的代码)发送代表plate对象的JS对象,并让模型绑定器为您构建对象。

当我查看您的代码时,PassCoordinates方法唯一要做的就是简单地设置Plate对象的Holes.coordinates属性值(您认为它在控制器中可用)。您可以完全删除该方法,并确保在表单中的输入元素中这样做,这样当您将表单提交给HttpPost索引操作方法时,它将在请求体中可用,模型绑定器将其映射到Plate参数。

@model Plate
@using (Html.BeginForm("Index", "Home"))
{      
@Html.TextBoxFor(a=>a.Holes.coordinates)       
<button type="submit" class="btn" >Save</button>    
}

这将在表单中创建一个名为Holes.coordinates的输入元素

<input id="Holes_coordinates" name="Holes.coordinates" type="text" value="">

输入一些值并提交表单。现在,如果您在HttpPost操作方法中放置断点,您可以看到您的板对象Hole proprety已填充,并且您可以访问在coordinates属性的文本框中输入的值。

现在,您所要做的就是,无论客户端代码进行ajax调用,而不是进行ajax调用时,都要设置此输入的值。

$("#Holes_coordinates").val("some value you want");

一旦一切正常,只需将调用切换到HiddenFor助手,就可以将可见的文本框转换为隐藏的输入。

@Html.HiddenFor(a=>a.Holes.coordinates)

如果您想在每个用户的请求之间维护状态

  • 使用TempData集合,并确保每次都设置值。它们将仅在下一个请求中可用,如果您希望它们保留多个请求,则必须每次设置它们
  • 使用会话存储用户当前会话的值:https://msdn.microsoft.com/en-us/library/ms178581.aspx
  • 将其储存在饼干中
  • 将其存储在查询字符串中
  • 将其存储在数据库中
  • 将其存储在内存数据库或缓存服务中
  • 通过模型将值返回到下一个返回的cshtml页面,并将值放置在输入表单字段中,以便通过下一个post在下一个请求中传递该值

每种方法都有优点和缺点,如果没有更多的信息,很难确定什么是合适的选择。

最新更新