0

I'm trying to use the new Html helper extension Serialize() from the furthure assembly..

If you take a look at:

View

<%@ Page Language="C#" Inherits="System.Web.Mvc.ViewPage<List<MvcApplication2.Models.ProductViewBinding>>" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<%@ Import Namespace="Microsoft.Web.Mvc" %>>

<html xmlns="http://www.w3.org/1999/xhtml" >
<head id="Head1" runat="server">
    <title>Index</title>
</head>
<body>
    <div>
    <% using (Html.BeginForm("Index", "Products", FormMethod.Post))
       { %>
       <% int codeIndex = 0;
           foreach (var item in Model)
          { %>
          <%: Html.TextBox("Encryption[" + codeIndex + "].Value") %>
          <%: Html.Serialize("Encryption[" + codeIndex + "].ID", item.ID) %>
          <% codeIndex++; 
        } %>
       <%: Html.SubmitButton("Click meh!") %>
    <% } %>
    </div>
</body>
</html>

Model

[Serializable] 
public class ProductViewBinding
{

    public object ID { get; set; }

    [NonSerialized]
    public object _value;
    public object Value 
    { 
        get { return this._value; } 
        set { this._value = value; } 
    }

}

Controller

[HttpPost]
public ActionResult Index([Deserialize] List<ProductViewBinding> Encryption)
{
    return View("Index", Encryption);
}

It returns null when posted... but if I remove the [Deserialize] attribute it returns as it should but with the ID still encrypted... Any suggestions for what I might be doing wrong?

1 Answer 1

4

I think you are missing the point of how the Serialize helper is supposed to work. You pass it an entire object graph which is serialized and stored in a hidden field that you could get back in a controller action using the [Deserialize] attribute. You cannot have half of your object serialized and the other half not.


UPDATE:

After seeing your comment here's a workaround:

Model:

public class ProductViewBinding
{
    public string ID { get; set; }
    public string Value { get; set; }
}

Controller:

public class HomeController : Controller
{
    public ActionResult Index()
    {
        var model = new[] 
        {
            new ProductViewBinding { ID = "1", Value = "value 1" }, 
            new ProductViewBinding { ID = "2", Value = "value 2" }, 
        };
        return View(model);
    }

    [HttpPost]
    public ActionResult Index(
        [Deserialize(SerializationMode.Encrypted)]string[] ids,
        string[] values
    )
    {
        IEnumerable<ProductViewBinding> model = values.Zip(
            ids, (id, value) => new ProductViewBinding { ID = id, Value = value }
        );
        return View("Index", model);
    }
}

View:

<%@ Page Language="C#" Inherits="System.Web.Mvc.ViewPage<SomeNs.Models.ProductViewBinding[]>" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<%@ Import Namespace="Microsoft.Web.Mvc" %>

<html xmlns="http://www.w3.org/1999/xhtml" >
<head id="Head1" runat="server">
    <title>Index</title>
</head>
<body>
    <% using (Html.BeginForm()) { %>
        <%: Html.Serialize("ids", Model.Select(x => x.ID).ToArray(), SerializationMode.Encrypted) %>
        <%for (int i = 0; i < Model.Length; i++) { %>
            <%: Html.TextBox("Values[" + i + "]", Model[i].Value) %>
        <% } %>
        <%: Html.SubmitButton("Click meh!") %>
    <% } %>
</body>
</html>

Notice the SerializationMode.Encrypted flag which is used if you want to achieve encryption, otherwise the user can tamper with the values.

Sign up to request clarification or add additional context in comments.

7 Comments

I see.. But what would be the right way to Encrypt a key into a hidden field thats used to identifie the textbox when its a List<>? The thing I was trying to do would be ideal if it worked.. because I only need the ID field to be serialized, not the textbox (Value)...
Works great! - However users can still tamper with the values?
No, they can't tamper with the IDS because they are encrypted. If someone tampers with the values you will get either null in the controller action or exception but a user won't be able to modify a value.
If I edit the value of the generated hidden field for "ids" it returns "invalid length for a base-64 char array", and if I just copy another Serialize field' value to the "ids" value then it's accepted?
Yes you should combine them into one.
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.