2010-09-08 3 views
0

Le nom est assez déroutant probablement. J'ai une exigence où une URL doit être nom convivial pour représenter les dates (schedule/today, schedule/tomorrow etc). Je ne pas veulent encombrer mes correspondances d'itinéraire avec DateTime.Now, DateTime.Now.AddDays(1) etc pour les paramètres différents donc j'ai décidé de créer des itinéraires qui correspondent à une action du même nom:Rendu d'action Vue du premier Action (lorsqu'une Action appelle une autre Action)

routes.MapRoute(RouteNames.ScheduleToday, "schedule/today", new { controller = "Schedule", action = "Today" }); 
routes.MapRoute(RouteNames.ScheduleTomorrow, "schedule/tomorrow", new { controller = "Schedule", action = "Tomorrow" }); 

L'idée pour les actions est que J'aimerais pouvoir appeler l'action Today() mais appeler l'action List(DateTime date) avec, par exemple, DateTime.Now comme paramètre date.

Cela fonctionne très bien comme ceci:

public ActionResult Today() 
{ 
    return this.List(DateTime.Now); 
} 

public ViewResult List(DateTime date) 
{ 
    this.ViewData["Date"] = date; 
    return this.View("List"); 
} 

Je voudrais pouvoir appeler this.View() au lieu de this.View("List"). Est-ce possible autre que ce que j'ai posté ci-dessus? Il semble que la vue affichée corresponde au nom de l'action première appelée car la seule façon de faire fonctionner cette option est de rendre explicitement la vue List.

Répondre

0

Je ne peux pas trouver pourquoi la première action qui est appelée correspond à la vue et non la dernière action (peut-être que je vais creuser dans la source). Pour le moment je m'en tiendrai à ce que j'ai car il n'y a pas de raison de trop compliquer les choses.

1

Je ne connais aucun moyen de rendre le View() sans paramètre renvoyer une vue autre que celle qui correspond au nom de la première méthode d'action. Mais que cette approche pour résoudre votre problème sans mettre DateTime.Now dans vos correspondances d'itinéraire - si vous définissez vos correspondances d'itinéraire comme ceci:

routes.MapRoute(RouteNames.ScheduleToday, "schedule/today", new { controller = "Schedule", action = "List", identifier = "today" }); 
routes.MapRoute(RouteNames.ScheduleTomorrow, "schedule/tomorrow", new { controller = "Schedule", action = "List", identifier = "tomorrow" }); 

Ici, nous avons mis en place un nouveau jeton d'itinéraire appelé « identifiant » ce qui correspond à ce que vous avez dans la route. L'autre chose que vous pouvez faire est de définir un itinéraire uniquecomme ceci:

routes.MapRoute(RouteNames.ScheduleToday, "schedule/{identifier}", new { controller = "Schedule", action = "List" }); 

Mais dans ce cas, vous voudriez une contrainte de route pour limiter votre jeton {identifiant} uniquement vos valeurs valides que vous soutenez . Avec ces routes en place, vous pouvez simplement créer un ActionFilterAttribute personnalisé qui a la responsabilité unique de la mise en place des dates.

Quelque chose comme ceci:

méthode
public class DateSelectorAttribute : ActionFilterAttribute 
{ 
    public override void OnActionExecuting(ActionExecutingContext filterContext) 
    { 
     var identifier = filterContext.RouteData.Values["identifier"] as string; 
     switch (identifier) 
     { 
      case "today": 
       filterContext.ActionParameters["date"] = DateTime.Now; 
       break; 
      case "tomorrow": 
       filterContext.ActionParameters["date"] = DateTime.Now.AddDays(1); 
       break; 
     } 
    } 
} 

Maintenant votre liste() peut simplement ressembler à ceci:

[DateSelector] 
public ActionResult List(DateTime date) 
{ 
    this.ViewData.Model = date; 
    return this.View(); 
} 

Et comme une note de côté, je me suis rendu la mise en place du DateTime.Now dans la Les routes ne fonctionneraient pas car elles ne seraient appelées qu'au démarrage de l'application, ce qui mettrait efficacement les valeurs de date en mémoire cache. Le filtre d'action est une meilleure approche car il est appelé en temps réel et vous donne la date exacte.

Espérons que cela aide.

+0

Ouais merci pour l'idée, mais je pense que c'est vraiment trop compliquer ce qui doit être fait. Appeler 'this.View (" List ")' est suffisant. – TheCloudlessSky

0

Ce que vous faites est erroné dans la façon dont vous redirigez vers une autre action de contrôleur à partir de Today(). Vous devriez utiliser l'une des surcharges RedirectToAction(). De cette façon, vous n'aurez pas à spécifier une vue dans l'action List(). Et vous pouvez fournir DateTime comme valeur de route à RedirectToAction().

+0

Ouais j'ai essayé ça aussi mais le problème c'est que ça redirigera l'URL aussi et mettra la date * dans * l'URL (ce qui est moche car je veux les garder amicaux). – TheCloudlessSky

Questions connexes