0

Net. Please help me. I have a void deletephoto method in my controller productmasters. The following is that method :

    [HttpPost]
    [ValidateAntiForgeryToken]
    public void DeletePhoto(ProductMaster productMaster,string id,string cid)
    {

       ProductMaster productMaster1 = (from p in db.ProductMasters
                        where p.ProductID == id && p.CompanyID == cid
                        select p).FirstOrDefault();

        string fullPath = Server.MapPath(productMaster1.ImagePathAndName);
        if (System.IO.File.Exists(fullPath))
        {
            System.IO.File.Delete(fullPath);
        }
        productMaster1.ImagePathAndName = null;
        productMaster1.Image = null;
        db.Entry(productMaster1).State = EntityState.Modified;
        db.SaveChanges();
    }

In my edit view I have a remove photo link:

<div>
   @Html.ActionLink("Remove Photo", "DeletePhoto", new { id = Model.ProductID, cid = Model.CompanyID })
</div>

The problem is: How can I execute the void method in this controller without refreshing the edit view.

Thanks in advance.

Michail Michailidis
  • 11,792
  • 6
  • 63
  • 106
Lakshmi
  • 1
  • 2
  • You need to use Ajax.. – Rajshekar Reddy Dec 22 '16 at 09:15
  • That's quite easy, you need just return JSON from your controller, then you can handle controller response via javascript/jquery/angular. – andrey.shedko Dec 22 '16 at 09:17
  • I tried AJAX but its not working properly.I am not an expert in AJax so can you please send a demo code? – Lakshmi Dec 22 '16 at 09:51
  • Your method is marked `[HttpPost]` and has `[ValidateAntiForgeryToken]` - a link only navigates to a GET method. You need a form, rendered with `@Html.AntiForgeryToken()` and you need to intercepts its submit event and make an ajax call –  Dec 22 '16 at 10:00
  • Thank you..Gonna try it. – Lakshmi Dec 22 '16 at 10:03

1 Answers1

1

Use Ajax.ActionLink instead of Html.ActionLink

Ajax.ActionLink is much like the Html.ActionLink counterpart, it also creates the hyperlink <a href="">Click here</a> but when the user clicks it and has a JavaScript enabled browser, Ajax.ActionLink sends the asynchronous request instead of navigating to the new URL. With the Ajax.ActionLink we specify what controller's action method is to be invoked and also specify what to do with the response coming back from the action method.

  @Ajax.ActionLink(
             "Remove Photo", // <-- Text to display
             "DeletePhoto", // <-- Action Method Name
             new { id = Model.ProductID, cid = Model.CompanyID },
             new AjaxOptions
             {
                 UpdateTargetId="PhotoDiv", // <-- DOM element ID to update
                 InsertionMode = InsertionMode.Replace, // <-- Replace the content of DOM element
                 HttpMethod = "GET" // <-- HTTP method
             })

EDIT If you have [ValidateAntiForgeryToken], you can simply use @Ajax.BeginForm

@Ajax.BeginForm("DeletePhoto", new { id = Model.ProductID, cid = Model.CompanyID }, new AjaxOptions { UpdateTargetId = "PhotoDiv" }))
{
  @Html.AntiForgeryToken()
  <input type="submit" value="Remove Photo" class="btnlink" /> // style button to look like a link by adding `btnLink` class
 }

CSS

.btnLink{
 background:none!important;
 border:none; 
 padding:0!important;
 font-family:arial,sans-serif; /*input has OS specific font-family*/
 color:#069;
 text-decoration:underline;
 cursor:pointer;
}
Senjuti Mahapatra
  • 2,570
  • 4
  • 27
  • 38
  • sorry its not working,it searches for the view page and returns :Server Error in '/' Application. The resource cannot be found. – Lakshmi Dec 22 '16 at 09:45
  • @Lakshmi: This is good [example](https://dyball.wordpress.com/2014/04/07/partial-view-using-unobtrusive-ajax-in-mvc-5-loads-into-a-new-page/) to start with and understand the basics. – Senjuti Mahapatra Dec 22 '16 at 10:04
  • The method is a POST, not a GET (and is decorated with `[ValidateAntiForgeryToken]`) –  Dec 22 '16 at 10:08
  • Enabling `UnobtrusiveJavaScriptEnabled` to true will solve that problem I suppose – Senjuti Mahapatra Dec 22 '16 at 10:12
  • @StephenMuecke: But yes, for `[ValidateAntiForgeryToken]`, `Ajax.BeginForm` will work – Senjuti Mahapatra Dec 22 '16 at 10:14
  • I know, but your answer is `Ajax.ActionLink()` :) –  Dec 22 '16 at 10:18
  • @StephenMuecke I have updated my answer now. Please check – Senjuti Mahapatra Dec 22 '16 at 10:26
  • It also not working..It returns an error: The anti-forgery token could not be decrypted. If this application is hosted by a Web Farm or cluster, ensure that all machines are running the same version of ASP.NET Web Pages and that the configuration specifies explicit encryption and validation keys. AutoGenerate cannot be used in a cluster. – Lakshmi Dec 22 '16 at 10:57
  • @Lakshmi Check this [link](http://stackoverflow.com/a/23402375/5619896), if it helps, because I had done the same coding earlier and it had worked. – Senjuti Mahapatra Dec 22 '16 at 11:02