2014-07-09 4 views
1

J'ai un @Html.ActionLink à l'intérieur d'une vue partielle qui, lorsqu'on clique dessus, j'aimerais soit envoyer l'utilisateur à une autre vue, soit rester dans la vue courante sans rien changer. Est-ce possible?MVC @ Html.ActionLink no-op du contrôleur

Notre contrôleur ressemble:

public ActionResult Edit(int id) 
{ 
    if (ShouldAllowEdit(id)) 
    { 
     return this.View("Edit", ...edit stuff...)    
    } 

    return ???????? 
} 

Nous avons essayé return new EmptyResult(); mais juste dumps l'utilisateur à une page blanche.

+0

Pourquoi le bouton est-il disponible pour qu'ils cliquent s'il est possible qu'ils ne puissent pas éditer? – Shoe

+0

Bonne question @Shoe. Ceci est à l'appui du verrouillage d'enregistrement sans une sorte d'actualisation active. Les utilisateurs verront que la chose qu'ils essayent d'éditer est actuellement verrouillée par un autre utilisateur, mais si son état a changé (c.-à-d. Été déverrouillé) depuis que le lien a été rendu, nous voulons les amener à l'écran d'édition lorsqu'ils cliquent sur le lien . – Chris

+0

Je pense qu'une meilleure approche consiste à utiliser ajax et en cas de succès, il redirige de javascript sinon ne rien faire. De cette façon, tout ce qui concerne l'état de la page reste intact en cas d'échec. – Shoe

Répondre

2

Ceci est une approche légèrement différente du problème, mais il devrait faire ce que vous voulez. Au lieu de donner à l'utilisateur un lien vers lequel naviguer, effectuez un appel ajax sur le lien/clic sur le bouton et effectuez la vérification de l'ID. Renvoie soit l'URL vers laquelle naviguer dans un JsonResult, soit rien si l'identifiant est invalide.

Au retour de l'appel ajax, accédez à l'URL si nécessaire.

(swap sur les ids codés en dur et == 0 avec votre fonction ShouldAllowEdit dans l'exemple bien sûr)

Dans la vue:

<div class="btn btn-danger" id="myButton">Button</div> 

@section scripts{ 
<script> 
    $("#myButton").click(function() { 
     $.ajax("@Url.Action("Edit", new { id = 0 })", { type : "POST" }) 
      .success(function (data) { 
       if (data.url !== "") { 
        window.location.href = data.url; 
       } 
      }); 
    }); 
</script> 
} 

Dans le contrôleur:

[HttpPost] 
public JsonResult Edit(int id) 
{ 
    if (id == 0) 
    { 
     return Json(new {url = ""}); 
    } 
    else 
    { 
     return Json(new { url = Url.Action("EditPage", new { id = id }) }); 
    } 
} 
+0

+1 De cette façon, la page reste dans le même état en cas d'échec. – Shoe

+1

Nous avons beaucoup de liens d'édition sur la page afin que cette stratégie fonctionne mieux avec '@ Ajax.ActionLink' Cela peut être spécifique au lien. Merci! – Chris

0

Si l'utilisateur clique sur un lien sera être enlevé. Ils peuvent être renvoyés directement à la même page, mais la page sera déchargée, sera à nouveau demandée au serveur, puis rendue dans le navigateur. Si vous ne voulez pas que cela se produise, vous ne donnez pas le lien à l'utilisateur en premier lieu. En d'autres termes, conditionnellement rendre le lien ou non en fonction des rôles de l'utilisateur ou quoi que ce soit.

@if (userCanEdit) 
{ 
    @Html.ActionLink(...) 
} 

Où est userCanEdit quelle que soit la logique que vous devez prendre cette décision.

Si l'utilisateur échoue à la vérification que vous déterminez, il n'obtient pas le lien. Simple.

Cependant, comme il y a des gens malveillants dans le monde, vous ne pouvez pas le laisser entièrement là. Il y a un potentiel pour l'utilisateur de trouver le lien pour éditer quelque chose et y aller manuellement. Donc, pour éviter que vous vérifiez la permission de modifier dans votre action (comme vous avez déjà dans votre exemple de code), mais si l'utilisateur n'a pas le droit, alors vous retourner juste un code d'état interdit:

return new HttpStatusCodeResult(HttpStatusCode.Forbidden); 

ou

return new HttpStatusCodeResult(403); 

Ils font tous les deux la même chose.

MISE À JOUR

Sur la base de votre commentaire ci-dessus, il semble que l'utilisateur est normalement autorisé à modifier mais ne peut pas dans un cas particulier parce qu'un autre utilisateur est l'édition. Un 403 Interdit n'est pas approprié dans ce cas, donc tout ce que vous avez est une simple redirection vers la page où ils étaient, peut-être avec un message expliquant pourquoi ils sont de retour là-bas.

TempData["EditErrorMessage"] = "Sorry another user is editing that right now."; 
return RedirectToAction("Index"); 
0

Une réponse est de rediriger vers l'action d'affichage - et peut-être donner un retour pourquoi ils ont échoué.

public ActionResult Edit(int id) 
{ 
    if (ShouldAllowEdit(id)) 
    { 
     return this.View("Edit", ...edit stuff...)    
    } 

    ModelState.AddModelError("id", "Not allowed to edit this item"); 
    return RedirectToAction(Edit(id)); 
} 
Questions connexes