Page is not refreshed by calling RedirectToAction - javascript

In the View I have a linked button and there is java scripts to collect information from view and then post to the corresponding action 'GroupDeny'
#Html.ActionLink("Deny Selected", "GroupDeny", null, new { #class = "denySelectedLink" })
#section Scripts {
#Scripts.Render("~/bundles/jqueryval")
<script type="text/javascript">
$(document).on('click', '.denySelectedLink', function (e) {
//Cancel original submission
e.preventDefault();
var identifiers = new Array();
//build the identifiers . . .
var jsonArg = JSON.stringify(identifiers);
$.post('/LicenseAssignment/GroupDeny?licensePermissionIdentifiers=' + encodeURIComponent(jsonArg));
});
</script>
Then in the controller, the GroupDeny will update the DB and then
call RedirecToAction in order to refresh the view
public class LicenseAssignmentController : Controller
{
[HttpPost]
public ActionResult GroupDeny(string licensePermissionIdentifiers)
{
// changes the DB
return RedirectToAction("Index");
}
// GET:
public async Task<ActionResult> Index()
{
var model = get data from DB
return View(model);
}
Everything seems work as expected, The Index will be called after the RedirectToAction("Index") is executed, and the model is update to date their when I watch it during debugging, the only problem is that the page is not refreshed at all, that is to say the view still keep unchanged, but after I refresh the page manually (press F5), the data will be updated with the values from DB

We use AJAX when we don't want to navigate away from the page. Your $.post() is an AJAX request.
Since you want navigation add a form to your page
#using(Html.BeginForm("GroupDeny", "LicenseAssignment", FormMethod.Post))
{
<input type="hidden" value=""
name="licensePermissionIdentifiers"
id="licensePermissionIdentifiers" />
}
Now submitting this form will navigate
$(document).on('click', '.denySelectedLink', function (e) {
e.preventDefault(); // prevent link navigation
var identifiers = new Array();
//build the identifiers . .
// populate the form values
$("#licensePermissionIdentifiers").val(identifiers);
$("form").submit();
});
The RedirectToAction() returns to the browser a 302 Redirect to LicenseAssignment/Index then you hit the Index action.

Since you are using Ajax you will have to redirect on the return of your $.post call and change your GroupDeny to a JsonResult.
Something like this maybe:
JS
$.post('/LicenseAssignment/GroupDeny?licensePermissionIdentifiers=' + encodeURIComponent(jsonArg), function(data){
if(data.Success){
//redirect
window.location.reload();
}else{
//handle error
}
});
Controller Action
[HttpPost]
public JsonResult GroupDeny(string licensePermissionIdentifiers)
{
// changes the DB
return Json(new { Success = true });
}

Related

Showing message box (alert) after submitig form

I have form in asp.net mvc
I want to show a alert message when user submit a form.
public ActionResult AddMessage(Message message)
{
If(ModelState.IsValid)
{
db.Messages.Add(message);
db.SaveChanges();
return RedirectToAction(“Index”);
}
else
{
return View();
}
}
The alert method is a JavaScript method which needs to be executed on client side, by the browser.
Since you are doing a normal form submit and you want to show the alert when ModelState.IsValid is true, you have to do that inside the view returned by index action.
You can use TempData to pass some data between your current action method code and the action method/view rendered by a redirect response.
public ActionResult AddMessage(Message message)
{
If(ModelState.IsValid)
{
db.Messages.Add(message);
db.SaveChanges();
TempData["Message"] = "Saved successfully";
return RedirectToAction(“Index”);
}
else
{
return View();
}
}
and in the view returned by Index action, you can check TempData["Message"] exist and if yes, read it and show it in an alert.
#section Scripts
{
<script>
#if(TempData["Message"]!=null)
{
#:alert("#TempData["Message"]");
}
</script>
}

Page not refreshing after making an ajax call

I have a webgrid am using and the grid has rows. I want to be able to delete
any row I want. I have a garbage icon on every row for deletion. If I click on
it, the javascript function DeleteTaskFromDb is called below
function DeleteTaskFromDb(processCompleteData) {
var url = "#Url.Action("RemoveTaskFromList", "Home")";
$.get(url, { 'objdata': processCompleteData }, function (data) {
//jQuery.removeData(data);
//$('#mainListContent').html(data);
});
}
In this method, I want to be able to redirect to EmployeeHoursDetail in same controller.
This is working. I hardcoded the uniqueId just for testing.
public ActionResult RemoveTaskFromList(string objdata)
{
Employeehourstaskinfo getAllTaskSaved = null;
try
{
var stripOffObjectName = JObject.Parse(objdata)["EmployeeTask"];
var cleanedData = JsonConvert.DeserializeObject<Employeetaskdto>(stripOffObjectName.ToString());
getAllTaskSaved = _dtcDataService.RemoveTaskRecordFromDb(cleanedData);
}
catch (Exception ex)
{
logger.Error(ex);
}
return RedirectToAction("EmployeeHoursDetail", "Home", new { uniqueId = 51207 });
}
This method returns the correct data i need i.e after deleting a record from above.
public ActionResult EmployeeHoursDetail(Int64 uniqueId = 0)
{
...//code here
...
getEmhourdetails = _dtcDataService.GetEmployeeHoursDetails(uniqueId);
return View(getEmhourdetails);
}
Problem : If I have 4 records on the webgrid and I delete 1, by the time my page reloads I can still see
the 4 records. It should only show 3 since i deleted one. I think my html page is not refreshing.
I suspect its my $.get call that is not refreshing the page.
How can I resolve this?

Can I send a message instead of a view back as an ActionResult with ASP.NET MVC4

I have the following action in ASP.NET MVC4
public ActionResult Register(RegisterModel model)
{
if (ModelState.IsValid)
{
// Attempt to register the user
try
{
WebSecurity.CreateUserAndAccount(model.UserName, model.Password);
WebSecurity.Login(model.UserName, model.Password);
// ?? Need some code here
}
catch (MembershipCreateUserException e)
{
ModelState.AddModelError("", ErrorCodeToString(e.StatusCode));
}
}
// If we got this far, something failed, redisplay form
return View(model);
}
I have the following code that calls this:
$('#article').on('submit', '#loginForm, #registerForm', function (e) {
e.preventDefault();
var $form = $(this);
var href= $form.attr('data-href');
$form.validate();
if (!$form.valid()) {
return false;
}
var data = $form.serializeArray();
$.ajax(
{
data: data,
type: 'POST',
url: href
})
.done(submitDone)
.fail(submitFail);
function submitDone(content) {
$('#article').html(content)
}
function submitFail() {
alert("Failed");
}
return false;
});
If the registration works I would like to force the whole web page to refresh. Is there
a way that I can send back a message from the actionmethod to the javascript to
tell it that the registration works and the javascript should refresh the whole
web page?
I did try return RedirectToLocal("/"); but this definitely does not work. What
this does is to return a new page and then have it populated in the #article DIV.
There is nothing that will automatically refresh the browser from the server.
To refresh the browser from the server you'll need to send something from the server to the client indicating that you want to refresh the page. You'll need to write the javascript to look for the indication to refresh the browser.
Client Code
function submitDone(content) {
var json = $.parseJson(content);
if(json.isSuccess) {
//Do something here
}
$('#article').html(json.content)
}
Server code
public ActionResult Register(RegisterModel model)
{
if (ModelState.IsValid)
{
// Attempt to register the user
try
{
WebSecurity.CreateUserAndAccount(model.UserName, model.Password);
WebSecurity.Login(model.UserName, model.Password);
// ?? Need some code here
}
catch (MembershipCreateUserException e)
{
ModelState.AddModelError("", ErrorCodeToString(e.StatusCode));
}
}
// If we got this far, something failed, redisplay form
return Json(new {isSuccess = true, content = model});
}
I am unsure of what you are trying to accomplish by refreshing the page, if it's to clear out the form fields. The same could be achieved by using JavaScript. By using javascript instead of a page refresh you won't lose page state, such as error messages.
well i can think of a quick javascript trick to refresh a page on success like this
function submitDone(content) {
window.location.reload();
}
this will reload the page on the success.

MVC3 Action Call from Javascript ReturnUrl parameter always null

I am using javascript to load up an Action and finding that when the action method is called one of the parameters "returnUrl" is always null. I have confirmed that returnUrl is populated in the javascript correctly using firebug, but somewhere between executing the .load function and the action method the value for returnUrl is lost and set to null. I have found that if I remove the "id" parameter and just have the "returnUrl" parameter that returnUrl has the correct value. I have spent many hours trying to figure out what is going on here and am completely stumped, I would apprectiate some help.
My Javascript:
<!-- Review Dialog Popup -->
<script type="text/javascript">
function showWriteReviewDialog(gameId, returnUrl) {
if( $("#Review").length == 0)
{
var url = "#Url.Action("WriteUserReview", "UGDBUser", new { id = "PLACEHOLDER", returnUrl = Request.Url.ToString() })";
// ajax load
$('#writereview').load(url.replace('PLACEHOLDER', gameId));
} else {
// clear summary & reviewtext fields
$('#summary,#reviewtext').val('');
//reopen the write review dialog which was previously rendered
$("#Review").dialog({
modal: true,
autoOpen: true,
resizeable: false
});
}
};
</script>
My Dumbed Down Action Method:
[Authorize]
public ActionResult WriteUserReview(Guid id, string returnUrl)
{
return Redirect(returnUrl);
}
There must be something wrong with the URL generated. Also make sure the id is a guid. Here is an example.
Option 1
function showWriteReviewDialog(gameId, returnUrl) {
var url = '#Url.Action("TestParams", "Home")?id=' + gameId + '&returnUrl=' + returnUrl;
$("#writereview").load(url);
//rest of your operations
};
Option 2
function showWriteReviewDialog(gameId, returnUrl) {
var url = '#Url.Action("TestParams", "Home", new { id = "guid_replace", returnUrl = "url_replace"})';
url = url.replace('guid_replace', gameId);
url = url.replace('url_replace', returnUrl);
$("#writereview").load(url);
//rest of your operations
};
Screen shot on hitting the action; it returns both the values (have a look at the watch window)

Inject something to ASP MVC Result

In my project I need to add functionality, that show infobox in right top corner of page, when client save something. Everything works fine when save operation do redirect to another page in my solution.
Client run save action:
[SaveAction] //my own action filter to show info box
public ActionResult Details(int id, FormCollection form)
{
var pojazd = PojazdRepo.GetById(id);;
if (UpdateAndSave(pojazd, form))
{
return RedirectToAction("Index");
}
else
{
return View(GetDetailsViewModel(id, true));
}
}
Now my action filter test that ModelState.IsValid is true then add something to TempData:
public class SaveActionAttribute : ActionFilterAttribute
{
private bool test;
private bool isAjax;
public override void OnActionExecuted(ActionExecutedContext ctx)
{
test = ctx.Controller.ViewData.ModelState.IsValid;
isAjax = ctx.HttpContext.Request.IsAjaxRequest();
base.OnActionExecuted(ctx);
}
public override void OnResultExecuting(ResultExecutingContext ctx)
{
if (test)
{
if (isAjax) ctx.Controller.TempData["ActionPopUp"] = "";
else ctx.Controller.TempData["ActionPopUp"] = "save";
}
base.OnResultExecuting(ctx);
}
}
And my Site.Master run script if TempData["ActionPopUp"] = "save":
<script type="text/javascript">
$(document).ready(function () {
var test = '<%: TempData["ActionPopUp"] %>';
if (test != '') SaveSuccessPopUp(test);
});
</script>
As mentioned, this solution works fine, when controller make Redirect and Site.Master is loaded again, my problem is, how to inject SaveSuccessPopUp() function to action result, when Action was called by AJAX and return something, what don't reload page and don't run Site.Master $(document).ready code block.
Nice question.
You need to probably work with partial view here. I mean if your request is an ajax request, append the TempData again and the TempData will be outputted inside the partial view.
How will you send that partial view output as chunk of html?
I have a blog post about how you can send the partial view as string. The topic is different but you will get the idea:
http://www.tugberkugurlu.com/archive/working-with-jquery-ajax-api-on-asp-net-mvc-3-0-power-of-json-jquery-and-asp-net-mvc-partial-views
Here is an example:
[HttpPost]
public ActionResult toogleIsDone(int itemId) {
//Getting the item according to itemId param
var model = _entities.ToDoTBs.FirstOrDefault(x => x.ToDoItemID == itemId);
//toggling the IsDone property
model.IsDone = !model.IsDone;
//Making the change on the db and saving
ObjectStateEntry osmEntry = _entities.ObjectStateManager.GetObjectStateEntry(model);
osmEntry.ChangeState(EntityState.Modified);
_entities.SaveChanges();
var updatedModel = _entities.ToDoTBs;
//returning the new template as json result
return Json(new { data = this.RenderPartialViewToString("_ToDoDBListPartial", updatedModel) });
}
RenderPartialViewToString is a controller extension. you can find the the complete code for that from below link:
https://bitbucket.org/tugberk/tugberkug.mvc/src/6cc3d3d64721/TugberkUg.MVC/Helpers/ControllerExtensions.cs
After you have your html back on the client side code, append it you DOM and work on it. Animate it, show/hide it, do whatever you need with it

Categories